Tuesday 30 June 2015

Dynamic Memory Allocation

DYNAMIC MEMORY ALLOCATION

Malloc, Sizeof, and Free

The malloc Function is used to allocate a block of memory on run time.

   void *malloc(number_of_bytes)

That is to say it returns a pointer of type void * that is the start in memory of the reserved portion of size number_of_bytes. If memory cannot be allocated a NULL pointer is returned.
Since a void * is returned the C standard states that this pointer can be converted to any type. The size_t argument type is defined in stdlib.h and is an unsigned type.
So:



    char *cp;
   cp = malloc(50);

attempts to get 50 bytes and assigns the start address to cp.
Also it is usual to use the sizeof() function to specify the number of bytes:


    int *ip;
   ip = (int *) malloc(100*sizeof(int));
 
Some C compilers may require to cast the type of conversion. The (int *) means coercion to an integer pointer. Coercion to the correct pointer type is very important to ensure pointer arithmetic is performed correctly. I personally use it as a means of ensuring that I am totally correct in my coding and use cast all the time.
It is good practice to use sizeof() even if you know the actual size you want -- it makes for device independent (portable) code.
sizeof can be used to find the size of any data type, variable or structure. Simply supply one of these as an argument to the function.

SO:



   int i;
   struct Node 
                  {
                    float x,y,z
                  };
   typedef struct Node sn;
 
   sizeof(int), sizeof(i),
   sizeof(struct Node) and
   sizeof(sn) are all ACCEPTABLE

In the above we can use the link between pointers and arrays to treat the reserved memory like an array. i.e we can do things like:

   ip[0] = 100;

or

   for(i=0;i<100;++i) scanf("%d",ip++);


When you have finished using a portion of memory you should always free() it. This allows the memory freed to be available again, possibly for further malloc() calls
The function free() takes a pointer as an argument and frees the memory to which the pointer refers.

Calloc and Realloc

There are two additional memory allocation functions, Calloc() and Realloc(). Their prototypes are given below:
void *calloc(size_t num_elements, size_t element_size};

void *realloc( void *ptr, size_t new_size);
Malloc does not initialise memory (to zero) in any way. If you wish to initialise memory then use calloc. Calloc there is slightly more computationally expensive but, occasionally, more convenient than malloc. Also note the different syntax between calloc and malloc in that calloc takes the number of desired elements, num_elements, and element_size, element_size, as two individual arguments.
Thus to assign 100 integer elements that are all initially zero you would do:


    int *ip;
   ip = (int *) calloc(100, sizeof(int));
Realloc is a function which attempts to change the size of a previous allocated block of memory. The new size can be larger or smaller. 
 If the block is made larger then the old contents remain unchanged and memory is added to the end of the block. If the size is made smaller then the remaining contents are unchanged.
  If the original block size cannot be resized then realloc will attempt to assign a new block of memory and will copy the old block contents.
 Note a new pointer (of different value) will consequently be returned. You must use this new value. If new memory cannot be reallocated then realloc returns NULL.
Thus to change the size of memory allocated to the *ip pointer above to an array block of 50 integers instead of 100, simply do:
   ip = (int *) calloc( ip, 50);

Monday 8 June 2015

MultiProcessor Overview



Multiprocessors

Definition:
A Multiprocessor is an interconnection of two or more CPUs between memory and IO devices. The term ‘processor’ in multiprocessor can mean either a CPU or an input-output processor(IOP). However, a system with a single CPU and one or more IOPs is usually not included in the definition of a multiprocessor system unless the IOP has computational facilities comparable to a CPU. As it is most commonly defined, a multiprocessor system implies the existence of multiple CPUs, although usually there will be one or more IOPs as well.


         Bus-based multiprocessors

Flynn’s Classification of multiple-processor machines:
{SI, MI} x {SD, MD} = {SISD, SIMD, MISD, MIMD}
SISD = Single Instruction Single Data
            Classical Von Neumann machines.
SIMD = Single Instruction Multiple Data
             Also called Array Processors or
     Data Parallel machines.
MISD Does not exist.
MIMD Multiple Instruction Multiple Data
     Control parallelism.

A Taxonomy of Parallel Computers
                                
NUMA          Non Uniform Memory Access
COMA          Cache Only Memory Access
MPP              Massively Parallel Processor
COW             Cluster Of Workstations
CC-NUMA    Cache Coherent NUMA
NC-NUMA   No Cache NUMA
Characteristics of Multiprocessors
􀂋 Multiprocessors System = MIMD
􀁺 An interconnection of two or more CPUs with memory and I/O equipment
» a single CPU and one or more IOPs is usually not included in a multiprocessor system
􀂄 Unless the IOP has computational facilities comparable to a CPU
􀂋 Computation can proceed in parallel in one of two ways
􀁺 1) Multiple independent jobs can be made to operate in parallel
􀁺 2) A single job can be partitioned into multiple parallel tasks
􀂋 Classified by the memory Organization
􀁺 1) Shared memory or Tightly-coupled system
» Local memory + Shared memory
􀂄 higher degree of interaction between tasks
􀁺 2) Distribute memory or Loosely-coupled system
» Local memory + message passing scheme (packet or message )
􀂄 most efficient when the interaction between tasks is minimal