0% found this document useful (0 votes)
37 views11 pages

COding

The document discusses coding principles and guidelines for writing quality code. It covers common coding errors like memory leaks, null dereferencing, and off-by-one errors. It also discusses structured programming and practices like information hiding, robustness, and avoiding empty code blocks.

Uploaded by

jaya
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
37 views11 pages

COding

The document discusses coding principles and guidelines for writing quality code. It covers common coding errors like memory leaks, null dereferencing, and off-by-one errors. It also discusses structured programming and practices like information hiding, robustness, and avoiding empty code blocks.

Uploaded by

jaya
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 11

CODING

The goal of the coding or programming activity is to


implement the design in the best possible manner. The
coding activity affects both testing and maintenance
profoundly. The goal during this phase is not to simplify
the job of the programmer. Rather, the goal should be to
simplify the job of the tester and the maintainer.
Programming Principles and Guidelines:
The main task before a programmer is to write
quality code with few bugs in it. The additional constraint
is to write code quickly. In this section, we will discuss
some concepts and practices that can help a
programmer write higher quality code. As a key task of a
programmer is to avoid errors in the programs, we first
discuss some common coding errors.
Common Coding Errors:
Software errors are a reality that all programmers
have to deal with. Much of effort in developing software
goes in identifying and removing bugs. There are various
practices that can reduce the occurrence of bugs, but
regardless of the tools or methods we use, bugs are
going to occur in programs. Though errors can occur in a
wide variety of ways, some types of errors are found
more commonly. Here we give a list of some of the
commonly occurring bugs.
Memory Leaks:
A memory leak is a situation where the memory is
allocated to the program which is not freed subsequently.
This error is a common source of software failures which
occurs frequently in the languages which do not have

automatic garbage collection (like C, C++). They have


little impact in short programs but can have catastrophic
effect on long running systems.
Freeing an Already Freed Resource:
In general, in programs, resources are first allocated and
then freed. For example, memory is first allocated and
then deallocated. This error occurs when the programmer
tries to free the already freed resource.
NULL Dereferencing:
This error occurs when we try to access the contents
of a location that points to NULL. This is a commonly
occurring error which can bring a software system down.
It is also difficult to detect as it the NULL dereferencing
may occur only in some paths and only under certain
situations. Often improper initialization in the different
paths leads to the NULL reference statement.It can also
be caused because of aliases.
Lack of Unique Addresses:
Aliasing creates many problems, and among them is
violation of unique
addresses when we expect different addresses.
Synchronization Errors:
In a parallel program, where there are multiple
threads possibly accessing some common resources,
then synchronization errors are possible. some of which
are:
1. Deadlocks
2. Race conditions

3. Inconsistent synchronization
Deadlock is a situation in which one or more
threads mutually lock each other.
Array Index Out of Bounds:
Array index often goes out of bounds, leading to
exceptions. Care need to be taken to see that the array
index values are not negative and do not exceed their
bounds.
Arithmetic exceptions:
These include errors like divide by zero and
floating point exceptions. The result of these may
vary from getting unexpected results to termination
of the program.
Off by One:
This is one of the most common errors which can be
caused in many ways. For example, starting at 1 when
we should start at 0 or vice versa, writing <=N instead of
< N or vice versa, and so on.
Enumerated data types:
Overflow and underflow errors can easily occur when
working with enumerated types, and care should be
taken when assuming the values of enumerated data
types.
Illegal use of & instead of &&:
This bug arises if non short circuit logic (like & or |) is
used instead of short circuit logic (&& or ||). Non short
circuit logic will evaluate both sides of the expression.
But short circuit operator evaluates one side and based
on the result, it decides if it has to evaluate the other
side or not.

String handling errors:


There are a number of ways in which string handling
functions like strcpy, sprintf, gets etc can fail. Examples
are one of the operands is NULL, the string is not NULL
terminated, or the source operand may have greater size
than the destination. String handling errors are quite
common.
Buffer overflow:
Though buffer overflow is also a frequent cause of
software failures, in today world its main impact is that it
is a security flaw that can be exploited by a malicious
user for executing arbitrary code.
Structured programing:
As stated earlier the basic objective of the coding
activity is to produce programs that are easy to
understand. It has been argued by many that structured
programming practice helps develop programs that are
easier to understand. Structured programming is often
regarded as "goto-less" programming.
A program has a static structure as well as a dynamic
structure. The static structure is the structure of the text
of the program, which is usually just a linear organization
of statements of the program. The dynamic structure of
the program is the sequence of statements executed
during the execution of the program. In other words, both
the static structure and the dynamic behaviour are
sequences of statements; where the sequence
representing the static structure of a program is fixed,
the sequence of statements it executes can change from
execution to execution.

The goal of structured programming is to ensure that


the static structure and the dynamic structures are the
same. That is, the objective of structured programming is
to write programs so that the sequence of statements
executed during the execution of a program is the same
as the sequence of statements in the text of that
program.
The key property of a structured statement is that it
has a single-entry and a single-exit That is, during
execution, the execution of the (structured) statement
starts from one defined point and the execution
terminates at one defined point. With single-entry and
single-exit statements, we can view a program as a
sequence of (structured) statements. Hence, by using
single-entry and single-exit statements, the
correspondence between the static and dynamic
structures can be obtained.
Some Programming Practices:
The concepts discussed above can help in writing
simple and clear code with few bugs. There are many
programming practices that can also help towards that
objective. We discuss here a few rules that have been
found to make code easier to read as well as avoid some
of the errors.
Control Constructs: As discussed earlier, it is
desirable that as much as possible single-entry, singleexit constructs be used. It is also desirable to use a few
standard control constructs rather than using a wide
variety of constructs, just because they are available in
the language.
Gotos: Gotos should be used sparingly and in a
disciplined manner. If a goto must be used, forward

transfers (or a jump to a later statement) is more


acceptable than a backward jump.
Information Hiding: As discussed earlier,
information hiding should be supported where possible.
Only the access functions for the data structures should
be made visible while hiding the data structure behind
these functions.
User-Defined Types: Modern languages allow users
to define types
like the enumerated type. When such facilities are
available, they should
be exploited where applicable.
Nesting: If nesting of if-then-else constructs
becomes too deep, then the logic become harder to
understand. In case of deeply nested if-then-elses, it is
often difficult to determine the if statement to which a
particular else clause is associated. Where possible, deep
nesting should be avoided, even if it means a little
inefficiency.
Module Size: A programmer should carefully
examine any function with too many statements (say
more than 100). Large modules often will not be
functionally cohesive. There can be no hard-and-fast rule
about module sizes the guiding principle should be
cohesion and coupling.
Module Interface: A module with a complex
interface should be carefully examined. As a rule of
thumb, any module whose interface has more than five
parameters should be carefully examined and broken into
multiple modules with a simpler interface if possible.

Side Effects: When a module is invoked, it


sometimes has side effects of modifying the program
state beyond the modification of parameters listed in the
module interface definition.
Robustness: A program is robust if it does
something planned even for exceptional conditions. A
program might encounter exceptional conditions in such
forms as incorrect input, the incorrect value of some
variable, and overflow. If such situations do arise, the
program should not just "crash" or "core dump"; it should
produce some meaningful message and exit gracefully.
Switch case with default: If there is no default
case in a "switch" statement, the behaviour can be
unpredictable if that case arises at some point of time
which was not predictable at development stage. Such a
practice can result in a bug like NULL dereference,
memory leak, as well as other types of serious bugs. It is
a good practice to always include a default case.
Empty Catch Block: An exception is caught, but if
there is no action, it may represent a scenario where
some of the operations to be done are not performed.
Whenever exceptions are caught, it is a good practice to
take some default action, even if it is just printing an
error message.
Empty if, while Statement: A condition is checked
but nothing is done based on the check. This often occurs
due to some mistake and should be caught. Other similar
errors include empty finally, try, synchronized, empty
static method, etc. Such useless checks should be
avoided.
Read Return to be Checked: Often the return
value from reads is not checked, assuming that the read

returns the desired values. Sometimes the result from a


read can be different from what is expected, and this can
cause failures later. There may be some cases where
neglecting this condition may result in some serious
error.
Return From Finally Block: One should not return
from finally block, as cases it can create false beliefs. If a
value is returned both in exception and nonexception
scenarios. Hence at the caller site, the user will not be
able to distinguish between the two. Another interesting
case arises when we have a return from try block. In this
case, if there is a return in finally also, then the value
from finally is returned instead of the value from try.
Correlated Parameters: Often there is an implicit
correlation between the parameters. For example, in the
code segment, if "length" represents the size of BUFFER.
If the correlation does not hold, we can run into a serious
problem like buffer overflow. Hence, it is a good practice
to validate this correlation rather than assuming that it
holds. In general, it is desirable to do some counter
checks on implicit assumptions about parameters.
Trusted Data sources: Counter checks should be
made before accessing the input data, particularly if the
input data is being provided by the user or is being
obtained over the network.
Give Importance to Exceptions: Most
programmers tend to give less attention to the possible
exceptional cases and tend to work with the main flow of
events, control, and data. Though the main work is done
in the main path, it is the exceptional paths that often
cause software systems to fail. To make a software
system more reliable, a programmer should consider all

possibilities and write suitable exception handlers to


prevent failures or loss when such situations occur.
Coding Standards:
Coding standards provide rules and guidelines for
some aspects of programming in order to make code
easier to read. Most organizations who develop software
regularly develop their own standards.
In general, coding standards provide guidelines for
programmers regarding naming, file organization,
statements and declarations, and layout and comments.

You might also like