Question

If the two signal handling functions in 3000pc were replaced by one function, would there be...

If the two signal handling functions in 3000pc were replaced by one function, would there be any significant loss of functionality? Briefly explain

/* 3000pc.c */

2

3

4

5

6

7

8 #include <stdio.h>

9 #include <stdlib.h>

10 #include <unistd.h>

11 #include <sys/mman.h>

12 #include <errno.h>

13 #include <string.h>

14 #include <sys/types.h>

15 #include <sys/wait.h>

16 #include <semaphore.h>

17 #include <string.h>

18 #include <time.h>

19

20 #define QUEUESIZE 32

21 #define WORDSIZE 16

22

23 const int wordlist_size = 27;

24 const char *wordlist[] = {

25         "Alpha",

26         "Bravo",

27         "Charlie",

28         "Delta",

29         "Echo",

30         "Foxtrot",

31         "Golf",

32         "Hotel",

33         "India",

34         "Juliet",

35         "Kilo",

36         "Lima",

37         "Mike",

38         "November",

39         "Oscar",

40         "Papa",

41         "Quebec",

42         "Romeo",

43         "Sierra",

44         "Tango",

45         "Uniform",

46         "Victor",

47         "Whiskey",

48         "X-ray",

49         "Yankee",

50         "Zulu",

51         "Dash"

52 };

53

54 typedef struct entry {

55         char word[WORDSIZE];

56         sem_t lock;

57 } entry;

58

59 typedef struct shared {

60         int prod_waiting;

61         int con_waiting;

62         entry queue[QUEUESIZE];

63         int last_produced;

64         int last_consumed;

65         pid_t prod_pid;

66         pid_t con_pid;

67         int prod_count;

68         int con_count;

69 } shared;

70

71

72 void report_error(char *error)

73 {

74         fprintf(stderr, "Error: %s\n", error);

75 }

76

77 void usage_exit(char *progname)

78 {

79         fprintf(stderr,

80                 "Usage: %s <event count> <prod delay int> <con delay int>\n",

81                 progname);

82         exit(-1);

83 }

84

85 void producer_handler(int the_signal)

86 {

87         if (the_signal == SIGUSR1) {

88                 fprintf(stderr, "Producer received SIGUSR1.\n");

89                 return;

90

91         } else {

92                 fprintf(stderr, "Producer: No handler for for signal %d?!\n",

93                         the_signal);

94                 return;

95         }

96 }

97

98 void consumer_handler(int the_signal)

99 {

100         if (the_signal == SIGUSR1) {

101                 fprintf(stderr, "Consumer received SIGUSR1.\n");

102                 return;

103         } else {

104                 fprintf(stderr, "Consumer: No handler for for signal %d?!\n",

105                         the_signal);

106                 return;

107         }

108 }

109

110 void pick_word(char *word)

111 {

112         int pick;

113

114         pick = random() % wordlist_size;

115

116         strcpy(word, wordlist[pick]);

117 }

118

119 void wait_for_producer(shared *s)

120 {

121         struct timespec delay;

122         

123         delay.tv_sec = 100;

124         delay.tv_nsec = 0;

125

126         s->con_waiting = 1;

127         

128         while (s->con_waiting) {

129                 nanosleep(&delay, NULL);

130         }

131 }

132

133 void wait_for_consumer(shared *s)

134 {

135         struct timespec delay;

136         

137         delay.tv_sec = 100;

138         delay.tv_nsec = 0;

139

140         s->prod_waiting = 1;

141         

142         while (s->prod_waiting) {

143                 nanosleep(&delay, NULL);

144         }

145 }

146

147 void wakeup_consumer(shared *s)

148 {

149         if (s->con_waiting) {

150                 s->con_waiting = 0;

151                 kill(s->con_pid, SIGUSR1);

152         }

153 }

154

155 void wakeup_producer(shared *s)

156 {

157         if (s->prod_waiting) {

158                 s->prod_waiting = 0;

159                 kill(s->prod_pid, SIGUSR1);

160         }

161 }

162

163 void output_word(int c, char *w)

164 {

165         printf("Word %d: %s\n", c, w);

166 }

167

168 int queue_word(char *word, shared *s)

169 {

170         entry *e;

171         int current, retval;

172         

173         current = (s->last_produced + 1) % QUEUESIZE;

174

175         e = &s->queue[current];

176

177         sem_wait(&e->lock);

178

179         if (e->word[0] != '\0') {

180                 /* consumer hasn't consumed this entry yet */

181                 sem_post(&e->lock);

182                 wait_for_consumer(s);

183                 sem_wait(&e->lock);

184         }

185

186         if (e->word[0] != '\0') {

187                 fprintf(stderr, "ERROR: No room for producer after waiting!\n");

188                 retval = -1;

189                 goto done;

190         } else {

191                 strncpy(e->word, word, WORDSIZE);

192                 s->last_produced = current;

193                 s->prod_count++;

194                 wakeup_consumer(s);

195                 retval = 0;

196                 goto done;

197         }

198

199 done:

200         sem_post(&e->lock);

201         return retval;

202 }

203

204 int get_next_word(char *word, shared *s)

205 {

206         entry *e;

207         int current, retval;

208

209         current = (s->last_consumed + 1) % QUEUESIZE;

210

211         e = &s->queue[current];

212         

213         sem_wait(&e->lock);

214

215         if (e->word[0] == '\0') {

216                 /* producer hasn't filled in this entry yet */

217                 sem_post(&e->lock);

218                 wait_for_producer(s);

219                 sem_wait(&e->lock);

220         }

221

222         if (e->word[0] == '\0') {

223                 fprintf(stderr, "ERROR: Nothing for consumer after waiting!\n");

224                 retval = -1;

225                 goto done;

226         } else {

227                 strncpy(word, e->word, WORDSIZE);

228                 e->word[0] = '\0';

229                 s->last_consumed = current;

230                 s->con_count++;

231                 wakeup_producer(s);

232                 retval = 0;

233                 goto done;

234         }

235         

236 done:

237         sem_post(&e->lock);

238         return retval;

239 }

240

241 void producer(shared *s, int event_count, int producer_delay_interval)

242 {

243         char word[WORDSIZE];

244         int i;

245         struct sigaction signal_handler_struct;

246

247         memset (&signal_handler_struct, 0, sizeof(signal_handler_struct));

248         signal_handler_struct.sa_handler = producer_handler;

249

250         if (sigaction(SIGUSR1, &signal_handler_struct, NULL)) {

251             fprintf(stderr, "Producer couldn't register SIGUSR1 handler.\n");

252         }

253         

254         for (i=0; i < event_count; i++) {       

255                 pick_word(word);

256                 queue_word(word, s);

257                 if (producer_delay_interval > 0) {

258                         if (i % producer_delay_interval == 0) {

259                                 sleep(1);

260                         }

261                 }

262         }

263

264         printf("Producer finished.\n");

265         exit(0);

266 }

267

268 void consumer(shared *s, int event_count, int consumer_delay_interval)

269 {

270         char word[WORDSIZE];

271         int i;

272         struct sigaction signal_handler_struct;

273

274         memset (&signal_handler_struct, 0, sizeof(signal_handler_struct));

275         signal_handler_struct.sa_handler = consumer_handler;

276

277         if (sigaction(SIGUSR1, &signal_handler_struct, NULL)) {

278             fprintf(stderr, "Consumer couldn't register SIGUSR1 handler.\n");

279         }

280         

281         for (i=0; i < event_count; i++) {       

282                 get_next_word(word, s);

283                 output_word(s->con_count, word);

284                 if (consumer_delay_interval > 0) {

285                         if (i % consumer_delay_interval == 0) {

286                                 sleep(1);

287                         }

288                 }

289         }

290

291         printf("Consumer finished.\n");

292         exit(0);

293 }

294

295 void init_shared(shared *s)

296 {

297         int i;

298         

299         s->con_waiting = 0;

300         s->last_consumed = -1;

301

302         s->prod_waiting = 0;

303         s->last_produced = -1;

304         

305         s->prod_pid = -1;

306         s->con_pid = -1;

307

308         s->prod_count = 0;

309         s->con_count = 0;

310                 

311         for (i=0; i<QUEUESIZE; i++) {

312                 s->queue[i].word[0] = '\0';

313                 /* semaphore is shared between processes,

314                    and initial value is 1 (unlocked) */

315                 sem_init(&s->queue[i].lock, 1, 1);

316         }

317 }

318

319 int main(int argc, char *argv[])

320 {

321         int pid, count, prod_interval, con_interval;

322         

323         shared *s;

324

325         srandom(42);

326         

327         if (argc < 4) {

328                 if (argc < 1) {

329                         report_error("no command line");

330                         usage_exit(argv[0]);

331                 } else {

332                         report_error("Not enough arguments");

333                         usage_exit(argv[0]);

334                 }

335         }

336

337         count = atoi(argv[1]);

338         prod_interval = atoi(argv[2]);

339         con_interval = atoi(argv[3]);

340

341         s = (shared *) mmap(NULL, sizeof(shared),

342                              PROT_READ|PROT_WRITE,

343                              MAP_SHARED|MAP_ANONYMOUS, -1, 0);

344         

345         if (s == MAP_FAILED) {

346                 report_error(strerror(errno));

347         }

348         

349         init_shared(s);

350         

351         pid = fork();

352

353         if (pid) {

354                 /* producer */

355                 s->prod_pid = getpid();

356                 producer(s, count, prod_interval);

357         } else {

358                 /* consumer */

359                 s->con_pid = getpid();

360                 consumer(s, count, con_interval);

361         }

362         

363         /* This line should never be reached */

364         return -1;

365 }

0 0
Add a comment Improve this question Transcribed image text
Answer #1

Question : Why does a different version of stat(), lstat(), exist that treats symbolic links differently? Why isn't a different version needed for hard links?

Solution : Both the function stat and lstat is used to get description about a file. Both these functions return information about a file. In some cases, we need to find out information about the symbolic link, where it is pointing to, where the actual file resides and other things, in such cases lstat() is required,. lstat() is same as stat(, just that it gives information about the link, instead of the file, if the file is a symbolic link instead of an actual file.

In case of hardlinks we dont need any other specific function as, stat() already gives us the information that we need in case of hard links.

stat() reads the file and stores the file in the file buffer.

All these function return a stat structure, which contain all the possible information about the file, such as ID of the device containing the file, no. of hard links, userID of owner, groupId etc. all the information that can be needed in case of hard link can already be retrieved using stat(). thus, no other function is required for hard links.

Add a comment
Know the answer?
Add Answer to:
If the two signal handling functions in 3000pc were replaced by one function, would there be...
Your Answer:

Post as a guest

Your Name:

What's your source?

Earn Coins

Coins can be redeemed for fabulous gifts.

Not the answer you're looking for? Ask your own homework help question. Our experts will answer your question WITHIN MINUTES for Free.
Similar Homework Help Questions
  • Would u help me fixing this CODE With Debugging Code with GDB #include <stdio.h> #include <stdlib.h>...

    Would u help me fixing this CODE With Debugging Code with GDB #include <stdio.h> #include <stdlib.h> #define SIZE (10) typedef struct _debugLab { int i; char c; } debugLab; // Prototypes void PrintUsage(char *); void DebugOption1(void); void DebugOption2(void); int main(int argc, char **argv) { int option = 0; if (argc == 1) { PrintUsage(argv[0]); exit(0); } option = atoi(argv[1]); if (option == 1) { DebugOption1(); } else if (option == 2) { DebugOption2(); } else { PrintUsage(argv[0]); exit(0); } }...

  • In c programming The Consumer Submits processing requests to the producer by supplying a file name, its location and a character. It also outputs the contents of the file provided by the producer...

    In c programming The Consumer Submits processing requests to the producer by supplying a file name, its location and a character. It also outputs the contents of the file provided by the producer to the standard output. The Producer Accepts multiple consumer requests and processes each request by creating the following four threads. The reader thread will read an input file, one line at a time. It will pass each line of input to the character thread through a queue...

  • Combine two codes (code 1) to get names with(code 2) to get info: Code 1: #include<unistd.h>...

    Combine two codes (code 1) to get names with(code 2) to get info: Code 1: #include<unistd.h> #include<sys/types.h> #include<sys/stat.h> #include<fcntl.h> #include<dirent.h> #include<stdio.h> #include<stdlib.h> void do_ls(char []); int main(int argc,char *argv[]) { if(argc == 1) do_ls("."); else while(--argc){ printf("%s:\n",*++argv); do_ls(*argv); } } void do_ls(char dirname[]) { DIR *dir_ptr; struct dirent *direntp; if((dir_ptr = opendir(dirname)) == NULL) fprintf(stderr,"ls1:cannot open %s\n",dirname); else { while((direntp = readdir(dir_ptr)) != NULL) printf("%s\n",direntp->d_name); closedir(dir_ptr); } } ____________________________ code 2: #include <stdio.h> #include <sys/types.h> #include <sys/stat.h> void show_stat_info(char *,...

  • Read given code RaceOrNot3.c and write all possible outputs of the program. Assume there will be...

    Read given code RaceOrNot3.c and write all possible outputs of the program. Assume there will be no thread creation or joining failures or semaphore failures. If you believe there is only one possible output, you just need to write that output. #include <stdio.h> #include <stdlib.h> #include <pthread.h> #include <semaphore.h> #include <errno.h> sem_t s1; int c=0,x=0; void *UpdateC1(void *arg) {    int i;    for(i=0;i<2000000;i++)   {        sem_wait(&s1);        c++;   x++;        sem_post(&s1);    } } void *UpdateC2(void *arg) {    int i,x=0;    for(i=0;i<2999999;i++)   {        sem_wait(&s1);        c++;   x++;       ...

  • so in this code, it computes the sum 1+2+....+n but i want it to compute 2*(1+2+....+n)...

    so in this code, it computes the sum 1+2+....+n but i want it to compute 2*(1+2+....+n) using semaphores implement solution to the critical section problem #include #include int sum; /* this data is shared by the thread(s) */ void *runner(void *param); /* threads call this function */ int main(int argc, char *argv[]) { pthread_t tid; /* the thread identifier */ pthread_attr_t attr; /* set of thread attributes */ if (argc != 2) { fprintf(stderr,"usage: a.out \n"); return -1; } if...

  • Read given code and write all possible outputs of the program. Assume there will be no...

    Read given code and write all possible outputs of the program. Assume there will be no thread creation or joining failures or mutex failures. If you believe there i only one possible output, you just need to write that output. Code: #include <stdio.h> #include <stdlib.h> #include <pthread.h> #include <semaphore.h> #include <errno.h> sem_t s1; int c[2] = {0,1}; void *UpdateC1(void *arg) { int i; for(i=0;i<1000000;i++) { sem_wait(&s1); c[0]=(c[0]+1)%2; c[1]=(c[1]+1)%2; sem_post(&s1); } return NULL; } void *UpdateC2(void *arg) { int i; for(i=0;i<2000000;i++)...

  • Modify the programs so that each program can both receive and send messages alternatively. Note that when you run the two programs, you should run them in two different windows ( terminals). Y...

    Modify the programs so that each program can both receive and send messages alternatively. Note that when you run the two programs, you should run them in two different windows ( terminals). You should be able to send messages from one to the other and terminate them by entering "end" //msgl.cpp / Here's the receiver program. / #include #include #include #1nclude #include <stdlib.h> <stdio.h> <string.h> <errno.h> <unistd.h> #include <sys/types.h> #include <sys/ipc.h> Winclude <sys/msg.h> struct my msg st f long int...

  • Assume I don't understand C++ Can someone explain this program to me Line by Line? Basically...

    Assume I don't understand C++ Can someone explain this program to me Line by Line? Basically what each line actually does? whats the function? whats the point? Don't tell me what the program does as a whole, I need to understand what each line does in this program. #include #include #include #include #include #define SERVER_PORT 5432 #define MAX_LINE 256 int main(int argc, char * argv[]) {    FILE *fp;    struct hostent *hp;    struct sockaddr_in sin;    char *host;...

  • I am getting the Segmentation fault error on the Ubuntu machine but not on macOS. Any...

    I am getting the Segmentation fault error on the Ubuntu machine but not on macOS. Any help would be appreciated. /**** main.c ****/ #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <stdio.h> #include <stdlib.h> #include <time.h> #include <unistd.h> #include <pthread.h> #include <string.h> #define WORD_LEN 6 #define TOP 10 char * delim = "\"\'.“”‘’?:;-,—*($%)! \t\n\x0A\r"; struct Word { char word[30]; int freq; }; int threadCount; int fileDescriptor; int fileSize; off_t chunk; struct Word* wordArray; int arrIndex = 0; pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;...

  • In C using the following 2 files to create a 3rd file that uses multiple threads...

    In C using the following 2 files to create a 3rd file that uses multiple threads to improve performance. Split the array into pieces and each piece is handled by a different thread. Use 8 threads. run and compile in linux. #include <stdio.h> #include <sys/time.h> #define BUFFER_SIZE 4000000 int countPrime=0; int numbers[BUFFER_SIZE]; int isPrime(int n) { int i; for(i=2;i<n;i++) if (n%i==0) return 0; return 1; } int main() { int i; // fill the buffer for(i=0;i<BUFFER_SIZE;i++) numbers[i] = (i+100)%100000; //...

ADVERTISEMENT
Free Homework Help App
Download From Google Play
Scan Your Homework
to Get Instant Free Answers
Need Online Homework Help?
Ask a Question
Get Answers For Free
Most questions answered within 3 hours.
ADVERTISEMENT
ADVERTISEMENT
ADVERTISEMENT