December 1998
CA208: 'C' PROGRAMMING

QUESTION 2

Total Marks: 20 Marks

Click here to access other questions

SUGGESTED SOLUTIONS
Solutions and allocated marks are indicated in green.
Return to Question 2

 

 

 

In Unix, a file descriptor set (fd_set) is a data-structure in which each bit represents the availability of a different device in the system. In a system that only has a maximum of 32 distinct devices, a file descriptor set can be represented by data-type fd_set below. For example, if devices zero, three, and four becomes available, then this will be represented by an fd_set value of 25 (i.e., the binary value 00000000000000000000000000011001). The following question will require the definition of the following C functions:

typedef unsigned int fd_set;

fd_set FD_SET(fd_set p, int n);
fd_set FD_CLR(fd_set p, int n);
int FD_ISSET(fd_set p, int n);
int FDS_ACTIVE(fd_set p);

 

(a) What would be returned if the following expressions were evaluated: [5]
(i) 2 & 3
2

 

(ii) 3 | 9
11

 

(iii) 21 & (~4)
17

 

(iv) 1 << 3
8

 

(v) 21 >> 2
5

 

(b) Define a macro FD_ZERO, that takes a single argument that represents a fd_set, which initialise each bit of the file descriptor set to 0. [2]
#define FD_ZERO(p) ((p)=0)

/* OR */
#define FD_ZERO(p) (p=0)

/* OR */
#define FD_ZERO(p) p=0

one mark for defining FD_ZERO with one argument using a definite statement. One mark for the body of the macro.

 

(c) Define a function FD_SET, that returns as it's result a fd_set that augments the value represented by p such that the nth bit (the rightmost bit is bit 0) of fd_set is set to one, i.e., fd_set(5,1) should return 7. [4]
A definition of FD_SET (there will be many other possible answers):

fd_set FD_SET(fd_set p, int n) {
    return (p | (1<<n));
}

Two marks for creating a bitmask where the nth bit is set (i.e., 1<<n) - the students may have done this using an alternative technique. One mark for or-ing this result with the original fd_set. One mark for returning the result of the or.

 

(d) Define a function FD_CLR, that returns as it's result a fd_set that augments the value represented by p such that the nth bit (the rightmost bit is bit 0) of the file descriptor set to one, i.e., fd_clr(5,0) should return 4. [3]
A definition of FD_CLR (there will be many possible answers):

fd_set FD_CLR(fd_set p, int n) {
     return (p & (~(1<<n)));
}

One mark for creating a bitmask where the nth bit is set (i.e., 1<<n) - the students may have done this using an alternative technique. One mark for inverting the bit-mask using complement. One mark for and-ing this result with the original fd_set.

 

(e) Define a function FD_ISSET, that returns zero if the  nth bit (the rightmost bit is bit 0) of the file descriptor set is zero, and a non-zero value otherwise, i.e., fd_isset(5,2) returns an integer that is not zero, whereas fd_isset(5,1) return 0. [2]
A definition of FD_ISSET (there will be many other possible answers):

inf FD_ISSET(fd_set p, int n) {
     return (p & (1<<n));
}

One mark for creating a bitmask where the the nth bit is set (i.e., 1<<n) - the students may have done this using an alternative technique. One mark for and-ing this result with the original fd_set.

 

(f) Define a function FDS_ACTIVE, that returns the number of bits that are set within the file descriptor set. [4]
A definition of FDS_ACTIVE (there will be many other possible answers):

int FDS_ACTIVE(fd_set p) {
   int i, res;

   res = 0;
   for (i=0; i<32; i++)
      if (FD_SET(p,i)) res++;
   return res;
}

If the function FD_SET is used within FDS_ACTIVE, then use the following marking scheme:

  • One mark for checking all 32bits of the fd_set.
  • One mark for using FD_SET to check if the ith bit of the fd is set.
  • One mark for incrementing a counter if the ith bit is set.
  • One mark for returning the result.

Alternatively, for a solution such as:

int FDS_ACTIVE(fd_set p) {
   int i, res;

   res=0;
   for(i=0; i<32, i++) {
      if (p&l) res++;
      p = p>>l;
   }
   return res;

}

use the following marking scheme:

  • One mark for checking all 32bits of the fd_set.
  • One mark for incrementing a counter if the least significant bit is set.
  • One mark for shifting the fd set by one bit.
  • One mark for returning the result.