1 /*
2 * export_pvm.c
3 *
4 * Copyright (C) Malanchini Marzio - June 2003
5 *
6 * This file is part of transcode, a video stream processing tool
7 *
8 * transcode is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2, or (at your option)
11 * any later version.
12 *
13 * transcode is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with GNU Make; see the file COPYING. If not, write to
20 * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
21 *
22 */
23
24 #include "transcode.h"
25
26 #include <stdio.h>
27 #include <stdlib.h>
28
29 #include "pvm_version.h"
30 #include "pvm_interface.h"
31 #include "pvm_parser.h"
32 #include "external_codec.h"
33 #include "vob_pack_unpack.h"
34
35 #define MOD_NAME "export_pvm.so"
36 #define MOD_VERSION EXPORT_PVM_VERSION
37 #define MOD_CODEC "(video) * | (audio) *"
38
39 #define MAX_BUF 1024
40
41 #define MIN_TOT_NPROC 1
42 #define MIN_FRAME 10
43
44 static int verbose_flag=TC_QUIET;
45 static int capability_flag=-1; //all codecs are welcome
46
47 #define MOD_PRE pvm
48 #include "export_def.h"
49
50 static int s_merger_tid_audio[]={-1,-1},s_merger_tid_video[]={-1,-1},s_init_check=0;
51 static int s_merger_tid_system[]={-1,-1};
52 static int s_null_video_module=0,s_null_audio_module=0,s_sys_merger_started=-1;
53 static void *p_handle=NULL;
54 static pvm_func_t s_pvm_single_proc_audio,s_pvm_single_proc_video,s_pvm_fun_audio,s_pvm_fun_video,s_pvm_single_proc_system;
55 static pvm_config_env s_pvm_conf,*p_pvm_conf=NULL;
56
57 static char *p_par1=NULL,*p_par2=NULL;
58
59
60 extern pthread_mutex_t s_channel_lock;
61
adjust_ch(char * line,char ch)62 static void adjust_ch(char *line, char ch)
63 {
64 char *src = &line[strlen(line)];
65 char *dst = line;
66
67 //-- remove blanks from right and left side --
68 do { src--; } while ( (src != line) && (*src == ch) );
69 *(src+1) = '\0';
70 src = line;
71 while (*src == ch) src++;
72
73 if (src == line) return;
74
75 //-- copy rest --
76 while (*src)
77 {
78 *dst = *src;
79 src++;
80 dst++;
81 }
82 *dst = '\0';
83 }
84
f_pvm_balancer(char * p_option,pvm_func_t * p_func,int s_seq,int s_type)85 static void f_pvm_balancer(char *p_option,pvm_func_t *p_func,int s_seq,int s_type)
86 {
87 int s_cont,s_dummy,s_dummy1,s_rc;
88
89 if (!strcasecmp(p_option, "open"))
90 {
91 for(s_cont=0;s_cont<p_func->s_nproc;s_cont++)
92 p_func->p_used_tid[s_cont]=INT_MAX; /*setup to INT_MAX*/
93 p_func->s_current_tid=0; /*First tid*/
94 }
95 else if (!strcasecmp(p_option, "close"))
96 {
97 for(s_cont=0;s_cont<p_func->s_nproc;s_cont++)
98 p_func->p_used_tid[s_cont]=INT_MAX; /*setup to INT_MAX*/
99 }
100 else if (!strcasecmp(p_option, "set-seq"))
101 {
102 p_func->p_used_tid[p_func->s_current_tid]=s_seq;
103 }
104 else if (!strcasecmp(p_option, "first-free"))
105 {
106 for(s_cont=(((1+p_func->s_current_tid)==p_func->s_nproc)?0:(1+p_func->s_current_tid));((p_func->p_used_tid[s_cont]!=INT_MAX)&&(s_cont<p_func->s_current_tid));s_cont=((((1+s_cont)==p_func->s_nproc)?0:(1+s_cont)))); /*det the first task free*/
107 // for(s_cont=0;((p_func->p_used_tid[s_cont]!=INT_MAX)&&(s_cont<p_func->s_nproc));s_cont++); /*det the first task free*/
108 if ((s_cont<p_func->s_nproc)&&(p_func->p_used_tid[s_cont]==INT_MAX)) /*it's already assigned to a running task?*/
109 {
110 p_func->s_current_tid=s_cont; /*setting up the new task*/
111 if (verbose_flag & TC_DEBUG)
112 {
113 if (s_type== TC_VIDEO)
114 tc_log_info(MOD_NAME, "The new task for video is %d",s_cont);
115 else
116 tc_log_info(MOD_NAME, "The new task for audio is %d",s_cont);
117 }
118 }
119 else /*stop and wait for the first free task*/
120 {
121 if (verbose_flag & TC_DEBUG)
122 {
123 if (s_type== TC_VIDEO)
124 tc_log_info(MOD_NAME, "Waiting for a video free task...");
125 else
126 tc_log_info(MOD_NAME, "Waiting for an audio free task...");
127 }
128 s_cont=s_seq;
129 if (s_type== TC_VIDEO)
130 (int)f_pvm_set_recv(PVM_MSG_ENDTASK_VIDEO); /*set up to receive the PVM_MSG_ENDTASK_VIDEO*/
131 else
132 (int)f_pvm_set_recv(PVM_MSG_ENDTASK_AUDIO); /*set up to receive the PVM_MSG_ENDTASK_AUDIO*/
133 s_seq=f_pvm_recv(&s_dummy,(char *)&s_dummy1,&s_rc); /*Waiting for a free task */
134 (int)f_pvm_set_recv(s_cont); /*set up to receive the prev seq*/
135 for(s_cont=0;p_func->p_used_tid[s_cont]!=s_seq;s_cont++); /*det the task free*/
136 p_func->s_current_tid=s_cont; /*setting up the new task*/
137 if (verbose_flag & TC_DEBUG)
138 {
139 if (s_type== TC_VIDEO)
140 tc_log_info(MOD_NAME, "The new video task free is %d",s_cont);
141 else
142 tc_log_info(MOD_NAME, "The new audio task free is %d",s_cont);
143 }
144 }
145 }
146 }
147
f_help(void)148 static void f_help(void)
149 {
150 tc_log_info(MOD_NAME, "%s",MOD_VERSION);
151 tc_log_info(MOD_NAME, " -F configfile,[[nproc]:[maxproc]:[nfrxtask]]");
152 tc_log_info(MOD_NAME, " nproc,maxproc,nfrxtask override the parameter present in the config file");
153 tc_log_info(MOD_NAME, " List of known and supported codecs:");
154 f_help_codec(MOD_NAME);
155 }
156
157 #define PVM_DEINIT do { \
158 if (s_init_check == 1) { \
159 void *ret = f_init_pvm_func("close", p_handle); \
160 s_init_check = (ret != NULL) ?1 :0; /* uhm... -- Fromani */ \
161 } else { \
162 s_init_check -= 1; \
163 } \
164 } while (0)
165
166 #define PVM_CLOSE do { \
167 f_pvm_balancer("close", p_pvm_fun, 0, param->flag); \
168 f_pvm_master_start_stop("close", "tcpvmexportd", NULL, \
169 p_pvm_conf->s_nproc, p_pvm_conf->s_max_proc, p_pvm_fun); \
170 PVM_DEINIT; \
171 } while (0)
172
173 /* ------------------------------------------------------------
174 *
175 * open codec
176 *
177 * ------------------------------------------------------------*/
178
179 MOD_open
180 {
181 pvm_func_t *p_pvm_fun=NULL;
182 int s_null_module;
183
184 pthread_mutex_lock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
185 if(param->flag == TC_VIDEO)
186 {
187 s_null_module=s_null_video_module;
188 p_pvm_fun=&s_pvm_fun_video;
189 if (verbose_flag & TC_DEBUG)
190 tc_log_info(MOD_NAME, "enter in MOD_OPEN Video");
191 }
192 else
193 {
194 s_null_module=s_null_audio_module;
195 p_pvm_fun=&s_pvm_fun_audio;
196 if (verbose_flag & TC_DEBUG)
197 tc_log_info(MOD_NAME, "enter in MOD_OPEN Video");
198 }
199 if (!s_null_module)
200 {
201 if((f_pvm_multi_send(0,(char *)0,PVM_EXP_OPT_OPEN,p_pvm_fun))==-1)
202 {
203 PVM_CLOSE;
204 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
205 return TC_ERROR;
206 }
207 }
208 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
209 if (verbose_flag & TC_DEBUG)
210 tc_log_info(MOD_NAME, "exit MOD_OPEN Video");
211 return TC_OK;
212 }
213
214 /* ------------------------------------------------------------
215 *
216 * init codec
217 *
218 * ------------------------------------------------------------*/
219
220 MOD_init
221 {
222 char *p_file_to_open=NULL;
223 char *p_tmp=NULL;
224 char *p_vob_buffer=NULL;
225 char *p_argv[]={"-s",(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0};
226 char *p_argv_merger[]={"-s","-j",(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0};
227 char *p_argv_merger_sys[]={"-s","-j",(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0,(char*)0};
228 int s_cont = 1, s_contj = 2, s_contsys = 2, s_vob_buffer_size;
229 pvm_config_codec *p_conf_codec;
230 pvm_func_t *p_pvm_fun=NULL;
231 pvm_func_t *p_pvm_single_proc=NULL;
232 int *p_merger_tid,*p_merger_sys_tid=0;
233 int s_null_module=0;
234 pvm_config_merger *p_merger_conf=NULL;
235 char s_version[MAX_BUF];
236 static int s_msys=0;
237
238 pthread_mutex_lock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
239 if (verbose_flag & TC_DEBUG)
240 tc_log_info(MOD_NAME, "enter in MOD_INIT");
241 if (s_init_check==0)
242 {
243 s_init_check++; //do it only for the first time
244 memset((char *)&s_pvm_conf,'\0',sizeof(pvm_config_env));
245 p_pvm_conf=&s_pvm_conf;
246 if(vob->ex_v_fcc != NULL && strlen(vob->ex_v_fcc) != 0)
247 {
248 p_par1 = tc_strdup(vob->ex_v_fcc); /* ...and memleaks for all! */
249 adjust_ch(p_par1, ' '); /*-- module to recall --*/
250 if(!strcasecmp(p_par1,"list"))
251 {
252 f_help();
253 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
254 return TC_ERROR;
255 }
256 p_pvm_conf = pvm_parser_open(p_par1, verbose, 0);
257 if (p_pvm_conf == NULL)
258 {
259 tc_log_warn(MOD_NAME, "error checking %s",p_par1);
260 f_help();
261 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
262 return TC_ERROR;
263 }
264 ac_memcpy((char *)&s_pvm_conf,(char *)p_pvm_conf,sizeof(pvm_config_env));
265 p_pvm_conf=&s_pvm_conf;
266 }
267 else //need at least the config file
268 {
269 f_help();
270 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
271 return TC_ERROR;
272 }
273 if(vob->ex_a_fcc != NULL && strlen(vob->ex_a_fcc) != 0)
274 {
275 p_par2 = tc_strdup(vob->ex_a_fcc);
276 adjust_ch(p_par2, ' '); /*-- first parameter of the module --*/
277 if (p_par2[0]==':')
278 {
279 if (p_pvm_conf->s_nproc==0)
280 p_pvm_conf->s_nproc=1; /*default nproc per host*/
281 if (p_par2[1]==':')
282 {
283 if (p_pvm_conf->s_max_proc==0)
284 p_pvm_conf->s_max_proc=10;
285 }
286 else
287 {
288 p_tmp=strtok(p_par2,":");
289 if (p_tmp==NULL)
290 {
291 if (p_pvm_conf->s_max_proc==0)
292 p_pvm_conf->s_max_proc=10;
293 }
294 else
295 {
296 p_pvm_conf->s_max_proc=atoi(p_tmp);
297 p_pvm_conf->s_max_proc=(p_pvm_conf->s_max_proc<MIN_TOT_NPROC)?10:p_pvm_conf->s_max_proc; /*the max is set to 10*/
298 }
299 }
300 p_tmp=strtok(NULL,":");
301 if (p_tmp==NULL)
302 {
303 if (p_pvm_conf->s_num_frame_task==0)
304 p_pvm_conf->s_num_frame_task=100;
305 }
306 else
307 {
308 p_pvm_conf->s_num_frame_task=atoi(p_tmp);
309 p_pvm_conf->s_num_frame_task=(p_pvm_conf->s_num_frame_task<MIN_FRAME)?100:p_pvm_conf->s_num_frame_task; /*the to the default */
310 }
311 }
312 else
313 {
314 p_pvm_conf->s_nproc=atoi(strtok(p_par2,":"));
315 p_pvm_conf->s_nproc=((p_pvm_conf->s_nproc)<1)?1:p_pvm_conf->s_nproc; /*the min is set to 2*/
316 p_tmp=strtok(NULL,":");
317 if (p_tmp==NULL)
318 {
319 if (p_pvm_conf->s_max_proc==0)
320 p_pvm_conf->s_max_proc=10;
321 }
322 else
323 {
324 p_pvm_conf->s_max_proc=atoi(p_tmp);
325 p_pvm_conf->s_max_proc=(p_pvm_conf->s_max_proc<MIN_TOT_NPROC)?10:p_pvm_conf->s_max_proc; /*the max is set to 10*/
326 }
327 p_tmp=strtok(NULL,":");
328 if (p_tmp==NULL)
329 {
330 if (p_pvm_conf->s_num_frame_task==0)
331 p_pvm_conf->s_num_frame_task=100;
332 }
333 else
334 {
335 p_pvm_conf->s_num_frame_task=atoi(p_tmp);
336 p_pvm_conf->s_num_frame_task=(p_pvm_conf->s_num_frame_task<MIN_FRAME)?100:p_pvm_conf->s_num_frame_task;
337 }
338 }
339 }
340 }
341 else
342 {
343 s_init_check++;
344 }
345 if(param->flag == TC_VIDEO)
346 {
347 p_conf_codec=&(p_pvm_conf->s_video_codec);
348 p_file_to_open = tc_strdup(vob->video_out_file);
349 p_merger_conf=&(p_pvm_conf->s_video_merger);
350 }
351 else
352 {
353 p_conf_codec=&(p_pvm_conf->s_audio_codec);
354 if (vob->audio_out_file !=NULL)
355 p_file_to_open = tc_strdup(vob->audio_out_file);
356 else
357 p_file_to_open = tc_strdup(vob->video_out_file);
358 p_merger_conf=&(p_pvm_conf->s_audio_merger);
359 }
360 if (p_pvm_conf->p_multiplex_cmd!=NULL)
361 {
362 p_argv_merger_sys[s_contsys++]="-x";
363 p_argv_merger_sys[s_contsys++]=p_pvm_conf->p_multiplex_cmd;
364 }
365 if (f_supported_export_module(p_conf_codec->p_codec))
366 {
367 p_argv[s_cont++]="-c";
368 p_argv[s_cont++]=p_conf_codec->p_codec; /*store the parameter*/
369 p_argv_merger[s_contj++]="-c";
370 p_argv_merger[s_contj++]=p_conf_codec->p_codec; /*store the parameter*/
371 p_argv_merger_sys[s_contsys++]="-c";
372 if ((p_argv_merger_sys[s_contsys++]=f_supported_system((pvm_config_codec *)&(p_pvm_conf->s_video_codec),(pvm_config_codec *)&(p_pvm_conf->s_audio_codec)))!=NULL)
373 {
374 if (p_pvm_conf->s_system_merger.p_hostname!=NULL)
375 {
376 if (vob->divxmultipass!=1)
377 s_sys_merger_started=0;
378 else /*if multipass == 1 i don't need to start the system merger*/
379 {
380 s_contsys--;
381 p_argv_merger_sys[s_contsys]="unknown"; /*store the parameter*/
382 s_sys_merger_started=-1; /*so the system merger never started*/
383 }
384 }
385 else
386 {
387 s_contsys--;
388 p_argv_merger_sys[s_contsys]="unknown"; /*store the parameter*/
389 s_sys_merger_started=-1; /*so the system merger never started*/
390 }
391 }
392 else
393 {
394 p_argv_merger_sys[s_contsys-1]="unknown"; /*store the parameter*/
395 s_sys_merger_started=-1; /*so the system merger never started*/
396 }
397 if (p_conf_codec->p_par1!=NULL)
398 if (p_conf_codec->p_par1[0]!=' ')
399 {
400 p_argv[s_cont++]="-1";
401 p_argv[s_cont++]=p_conf_codec->p_par1; /*store the parameter*/
402 p_argv_merger[s_contj++]="-1";
403 p_argv_merger[s_contj++]=p_conf_codec->p_par1; /*store the parameter*/
404 p_argv_merger_sys[s_contsys++]="-1";
405 p_argv_merger_sys[s_contsys++]=p_conf_codec->p_par1; /*store the parameter*/
406 }
407 if (p_conf_codec->p_par2!=NULL)
408 if (p_conf_codec->p_par2[0]!=' ')
409 {
410 p_argv[s_cont++]="-2";
411 p_argv[s_cont++]=p_conf_codec->p_par2; /*store the parameter*/
412 }
413 if (p_conf_codec->p_par3!=NULL)
414 if (p_conf_codec->p_par3[0]!=' ')
415 {
416 p_argv[s_cont++]="-3";
417 p_argv[s_cont++]=p_conf_codec->p_par3; /*store the parameter*/
418 }
419 }
420 else if (!strcasecmp(p_conf_codec->p_codec, "null"))
421 {
422 s_null_module=1;
423 if(param->flag == TC_VIDEO)
424 {
425 s_null_video_module=s_null_module;
426 tc_log_info(MOD_NAME, "use internal video null codec");
427 }
428 else
429 {
430 s_null_audio_module=s_null_module;
431 tc_log_info(MOD_NAME, "use internal audio null codec");
432 }
433 }
434 else
435 {
436 tc_log_warn(MOD_NAME, "unsupported %s codec",p_conf_codec->p_codec);
437 f_help(); /*unsupported codec parameter*/
438 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
439 return TC_ERROR;
440 }
441 if ((!strcasecmp(p_pvm_conf->s_audio_codec.p_codec, "null"))||(!strcasecmp(p_pvm_conf->s_video_codec.p_codec, "null")))
442 {
443 s_sys_merger_started=-1; /*so the system merger never started*/
444 p_pvm_conf->s_system_merger.p_hostname=NULL;
445 }
446 if (!s_null_module) /*skip if null module is requested*/
447 {
448 /*check the default setup*/
449 p_pvm_conf->s_nproc=(p_pvm_conf->s_nproc<1)?1:p_pvm_conf->s_nproc;
450 p_pvm_conf->s_max_proc=(p_pvm_conf->s_max_proc<MIN_TOT_NPROC)?10:p_pvm_conf->s_max_proc;
451 p_pvm_conf->s_num_frame_task=(p_pvm_conf->s_num_frame_task<MIN_FRAME)?100:p_pvm_conf->s_num_frame_task;
452
453 if ((vob->divxmultipass==0)&&(p_pvm_conf->s_internal_multipass))
454 {
455 p_argv[s_cont++]="-M"; /*use internale multipass only if -R option isn't set*/
456 }
457 else
458 {
459 p_argv_merger[s_contj++]="-p";
460 switch(vob->divxmultipass)
461 {
462 case 3:
463 p_argv_merger[s_contj++]="3";
464 break;
465 case 2:
466 p_argv_merger[s_contj++]="2";
467 break;
468 case 1:
469 p_argv_merger[s_contj++]="1";
470 break;
471 case 0:
472 default:
473 p_argv_merger[s_contj++]="0";
474 break;
475 }
476 }
477 p_argv[s_cont++]="-d";
478 p_argv_merger[s_contj++]="-d";
479 p_argv_merger_sys[s_contsys++]="-d";
480 if (verbose == 0)
481 {
482 p_argv[s_cont++]="0";
483 p_argv_merger[s_contj++]="0";
484 p_argv_merger_sys[s_contsys++]="0";
485 }
486 else if (verbose==1)
487 {
488 p_argv[s_cont++]="1";
489 p_argv_merger[s_contj++]="1";
490 p_argv_merger_sys[s_contsys++]="1";
491 }
492 else
493 {
494 p_argv[s_cont++]="2";
495 p_argv_merger[s_contj++]="2";
496 p_argv_merger_sys[s_contsys++]="2";
497 }
498 if (p_file_to_open !=NULL)
499 {
500 p_argv[s_cont++]="-f";
501 p_argv[s_cont++]=p_file_to_open; /*video/audio out file name*/
502 p_argv_merger[s_contj++]="-f";
503 p_argv_merger[s_contj++]=p_file_to_open; /*video/audio out file name*/
504 p_argv_merger_sys[s_contsys++]="-f";
505 p_argv_merger_sys[s_contsys++]=p_file_to_open;
506 }
507 p_argv_merger_sys[s_contsys++]="-L"; /*need to create system list every time*/
508 if (p_merger_conf->s_build_only_list)
509 p_argv_merger[s_contj++]="-L";
510 if ((verbose_flag & TC_INFO)||(verbose_flag & TC_DEBUG))
511 tc_log_info(MOD_NAME, "P1=%s, P2=%s (%d %d %d)",
512 p_par1,p_par2,p_pvm_conf->s_nproc,
513 p_pvm_conf->s_max_proc,
514 p_pvm_conf->s_num_frame_task);
515 if (p_handle==NULL)
516 {
517 if((p_handle=f_init_pvm_func("open",NULL))==NULL)
518 {
519 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
520 return TC_ERROR;
521 }
522 }
523 p_argv[s_cont++]="-t";
524 p_argv_merger[s_contj++]="-t";
525 p_argv_merger_sys[s_contsys++]="-t";
526 if (p_pvm_conf->s_system_merger.s_build_only_list==2)
527 p_argv_merger_sys[s_contsys++]="multisystem";
528 else
529 p_argv_merger_sys[s_contsys++]="system";
530 if (s_sys_merger_started==0)
531 {
532 memset((char *)&s_pvm_single_proc_system,'\0',sizeof(pvm_func_t));
533 s_pvm_single_proc_system.p_slave_tids=&s_merger_tid_system[0]; /*data for the merger process*/
534 s_pvm_single_proc_system.s_nproc=1;
535 s_pvm_single_proc_system.s_current_tid=0; /*data for the merger process*/
536 p_merger_sys_tid=(int *)&s_merger_tid_system[0];
537 }
538 if(param->flag == TC_VIDEO)
539 {
540 p_argv[s_cont++]="video"; /*video parameter*/
541 p_argv_merger[s_contj++]="video"; /*video parameter*/
542 memset((char *)&s_pvm_fun_video,'\0',sizeof(pvm_func_t));
543 p_pvm_fun=&s_pvm_fun_video;
544 p_merger_tid=&s_merger_tid_video[0];
545 memset((char *)&s_pvm_single_proc_video,'\0',sizeof(pvm_func_t));
546 p_pvm_single_proc=&s_pvm_single_proc_video;
547 p_pvm_single_proc->p_slave_tids=&s_merger_tid_video[0]; /*data for the merger process*/
548 }
549 else
550 {
551 p_argv[s_cont++]="audio"; /*audio parameter*/
552 p_argv_merger[s_contj++]="audio";/*audio parameter*/
553 memset((char *)&s_pvm_fun_audio,'\0',sizeof(pvm_func_t));
554 p_pvm_fun=&s_pvm_fun_audio;
555 p_merger_tid=&s_merger_tid_audio[0];
556 memset((char *)&s_pvm_single_proc_audio,'\0',sizeof(pvm_func_t));
557 p_pvm_single_proc=&s_pvm_single_proc_audio;
558 p_pvm_single_proc->p_slave_tids=&s_merger_tid_audio[0]; /*data for the merger process*/
559 }
560 p_pvm_single_proc->s_nproc=1; /*data for the merger process*/
561 p_pvm_single_proc->s_current_tid=0; /*data for the merger process*/
562 if (f_pvm_master_start_stop("open","tcpvmexportd",p_argv,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun)==NULL)
563 {
564 PVM_DEINIT;
565 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
566 return TC_ERROR;
567 }
568 memset((char *)&s_version,'\0',MAX_BUF);
569 tc_snprintf((char *)&s_version,MAX_BUF,"%s",EXPORT_PVM_VERSION);
570 if((f_pvm_multi_send(strlen(&s_version[0]),(char *)&s_version[0],PVM_CHECK_VERSION,p_pvm_fun))==-1)
571 {
572 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
573 PVM_DEINIT;
574 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
575 return TC_ERROR;
576 }
577 if (p_pvm_conf->s_system_merger.p_hostname!=NULL)
578 {
579 if ((s_sys_merger_started==0)&&(s_msys==0))
580 {
581 s_sys_merger_started=1; /*execute only 1 time*/
582 s_msys=1;
583 if ((*p_merger_sys_tid=f_pvm_start_single_process("tcpvmexportd",p_argv_merger_sys,p_pvm_conf->s_system_merger.p_hostname)) ==-1)
584 {
585 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
586 PVM_DEINIT;
587 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
588 return TC_ERROR;
589 }
590 if (verbose_flag & TC_DEBUG)
591 tc_log_info(MOD_NAME, "System merger tid %d",*p_merger_sys_tid);
592 /*send the output file name*/
593 if(f_pvm_send(strlen(p_file_to_open),(char *)p_file_to_open,PVM_JOIN_OPT_INIT,s_pvm_single_proc_system.s_current_tid,&s_pvm_single_proc_system)==-1)
594 {
595 f_pvm_stop_single_process(*p_merger_sys_tid);
596 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
597 PVM_DEINIT;
598 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
599 return TC_ERROR;
600 }
601 }
602 }
603 if ((*p_merger_tid=f_pvm_start_single_process("tcpvmexportd",p_argv_merger,p_merger_conf->p_hostname)) ==-1)
604 {
605 if (s_sys_merger_started==1)
606 s_sys_merger_started--;
607 else if (s_sys_merger_started==0)
608 f_pvm_stop_single_process(*p_merger_sys_tid);
609 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
610 PVM_DEINIT;
611 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
612 return TC_ERROR;
613 }
614 if (verbose_flag & TC_DEBUG)
615 tc_log_info(MOD_NAME, "MOD_INIT stop f_pvm_start_single_process");
616 if (verbose_flag & TC_DEBUG)
617 tc_log_info(MOD_NAME, "MOD_INIT start PVM_INIT_SKED");
618 if((f_pvm_multi_send(sizeof(int),(char *)&p_pvm_conf->s_num_frame_task,PVM_INIT_SKED,p_pvm_fun))==-1)
619 {
620 f_pvm_stop_single_process(*p_merger_tid);
621 if (s_sys_merger_started==1)
622 s_sys_merger_started--;
623 else if (s_sys_merger_started==0)
624 f_pvm_stop_single_process(*p_merger_sys_tid);
625 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
626 PVM_DEINIT;
627 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
628 return TC_ERROR;
629 }
630 if (verbose_flag & TC_DEBUG)
631 tc_log_info(MOD_NAME, "MOD_INIT stop PVM_INIT_SKED");
632 if (verbose_flag & TC_DEBUG)
633 {
634 if(param->flag == TC_VIDEO)
635 tc_log_info(MOD_NAME, "Video merger tid %d",*p_merger_tid);
636 else
637 tc_log_info(MOD_NAME, "Audio merger tid %d",*p_merger_tid);
638 }
639 if((f_pvm_multi_send(sizeof(int),(char *)p_merger_tid,PVM_INIT_JOIN,p_pvm_fun))==-1) /*send the merger tid*/
640 {
641 f_pvm_stop_single_process(*p_merger_tid);
642 if (s_sys_merger_started==1)
643 s_sys_merger_started--;
644 else if (s_sys_merger_started==0)
645 f_pvm_stop_single_process(*p_merger_sys_tid);
646 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
647 PVM_DEINIT;
648 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
649 return TC_ERROR;
650 }
651 /*initial send of the vob structures to the slave processes*/
652 p_vob_buffer=f_vob_pack("open",vob,&s_vob_buffer_size);
653 if (vob->divxmultipass==2)
654 {
655 if (verbose_flag & TC_DEBUG)
656 tc_log_info(MOD_NAME, "enter in preinit msg");
657 for(s_cont=0;s_cont<p_pvm_fun->s_nproc;s_cont++)
658 {
659 if(f_pvm_send(sizeof(int),(char *)&s_cont,PVM_EXP_OPT_PREINIT,s_cont,p_pvm_fun)==-1)
660 {
661 f_pvm_stop_single_process(*p_merger_tid);
662 if (s_sys_merger_started==1)
663 s_sys_merger_started--;
664 else if (s_sys_merger_started==0)
665 f_pvm_stop_single_process(*p_merger_sys_tid);
666 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
667 PVM_DEINIT;
668 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
669 return TC_ERROR;
670 }
671 }
672 if (verbose_flag & TC_DEBUG)
673 tc_log_info(MOD_NAME, "exit from preinit msg");
674 }
675 if((f_pvm_multi_send(s_vob_buffer_size,p_vob_buffer,PVM_EXP_OPT_INIT,p_pvm_fun))==-1)
676 {
677 f_pvm_stop_single_process(*p_merger_tid);
678 if (s_sys_merger_started==1)
679 s_sys_merger_started--;
680 else if (s_sys_merger_started==0)
681 f_pvm_stop_single_process(*p_merger_sys_tid);
682 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
683 PVM_DEINIT;
684 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
685 return TC_ERROR;
686 }
687 (char *)f_vob_pack("close",NULL,&s_vob_buffer_size);
688 if(f_pvm_send(strlen(p_file_to_open),(char *)p_file_to_open,PVM_JOIN_OPT_INIT,p_pvm_single_proc->s_current_tid,p_pvm_single_proc)==-1)
689 {
690 f_pvm_stop_single_process(*p_merger_tid);
691 if (s_sys_merger_started==1)
692 s_sys_merger_started--;
693 else if (s_sys_merger_started==0)
694 f_pvm_stop_single_process(*p_merger_sys_tid);
695 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
696 PVM_DEINIT;
697 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
698 return TC_ERROR;
699 }
700 if (s_msys==1)
701 {
702 if(f_pvm_send(sizeof(int),(char *)p_merger_sys_tid,PVM_MERGER_INIT,p_pvm_single_proc->s_current_tid,p_pvm_single_proc)==-1)
703 {
704 f_pvm_stop_single_process(*p_merger_tid);
705 if (s_sys_merger_started==1)
706 s_sys_merger_started--;
707 else if (s_sys_merger_started==0)
708 f_pvm_stop_single_process(*p_merger_sys_tid);
709 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
710 PVM_DEINIT;
711 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
712 return TC_ERROR;
713 }
714 }
715 }
716 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
717 if (verbose_flag & TC_DEBUG)
718 tc_log_info(MOD_NAME, "exit from MOD_INIT");
719 return TC_OK;
720 }
721
722
723 /* ------------------------------------------------------------
724 *
725 * encode and export
726 *
727 * ------------------------------------------------------------*/
728
729 MOD_encode
730 {
731 static int s_video_cont=0,s_audio_cont=0,s_video_seq=0,s_audio_seq=0;
732 static char *p_video_buffer=NULL,*p_audio_buffer=NULL;
733 pvm_func_t *p_pvm_fun=NULL;
734 char *p_buffer=NULL;
735 int s_seq,s_cont=0;
736 int *p_merger_tid=0,*p_merger_sys_tid=0;
737 int s_null_module;
738
739 pthread_mutex_lock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
740 p_merger_sys_tid=(int *)&s_merger_tid_system[0];
741 if(param->flag == TC_VIDEO)
742 {
743 s_null_module=s_null_video_module;
744 if (!s_null_module)
745 {
746 p_pvm_fun=&s_pvm_fun_video;
747 p_buffer=p_video_buffer;
748 s_seq=s_video_seq;
749 p_merger_tid=&s_merger_tid_video[0];
750 s_cont=s_video_cont;
751 }
752 }
753 else
754 {
755 s_null_module=s_null_audio_module;
756 if (!s_null_module)
757 {
758 p_pvm_fun=&s_pvm_fun_audio;
759 p_buffer=p_audio_buffer;
760 s_seq=s_audio_seq;
761 p_merger_tid=&s_merger_tid_audio[0];
762 s_cont=s_audio_cont;
763 }
764 }
765 if (!s_null_module)
766 {
767 if (p_buffer==NULL)
768 {
769 p_buffer=(char *)malloc(sizeof(transfer_t)+param->size);
770 f_pvm_balancer("open",p_pvm_fun,0,param->flag);
771 }
772 (int)f_pvm_set_send(s_seq); /*set the seq number*/
773 ac_memcpy(p_buffer,(char *)param,sizeof(transfer_t));
774 ac_memcpy(p_buffer+sizeof(transfer_t),(char *)param->buffer,param->size);
775 if((s_seq=f_pvm_send((sizeof(transfer_t)+param->size),(char *)p_buffer,PVM_EXP_OPT_ENCODE,p_pvm_fun->s_current_tid,p_pvm_fun))==-1)
776 {
777 f_pvm_stop_single_process(*p_merger_tid);
778 if (s_sys_merger_started==1)
779 s_sys_merger_started--;
780 else if (s_sys_merger_started==0)
781 f_pvm_stop_single_process(*p_merger_sys_tid);
782 PVM_CLOSE;
783 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
784 return TC_ERROR;
785 }
786 if (verbose_flag & TC_DEBUG)
787 {
788 if(param->flag == TC_VIDEO)
789 tc_log_info(MOD_NAME,"Send %d video sequence number",s_seq);
790 else
791 tc_log_info(MOD_NAME,"Send %d audio sequence number",s_seq);
792 }
793 f_pvm_balancer("set-seq",p_pvm_fun,s_seq,param->flag); /*the tid in s_tid_pos now elab the seq*/
794 if (s_cont<p_pvm_conf->s_num_frame_task)
795 {
796 s_cont++;
797 }
798 else
799 {
800 (int)f_pvm_set_send(s_seq); /*set the prev. seq number*/
801 if((s_seq=f_pvm_send(0,(char *)0,PVM_EXP_OPT_RESTART_ENCODE1,p_pvm_fun->s_current_tid,p_pvm_fun))==-1)
802 {
803 f_pvm_stop_single_process(*p_merger_tid);
804 if (s_sys_merger_started==1)
805 s_sys_merger_started--;
806 else if (s_sys_merger_started==0)
807 f_pvm_stop_single_process(*p_merger_sys_tid);
808 PVM_CLOSE;
809 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
810 return TC_ERROR;
811 }
812 f_pvm_balancer("first-free",p_pvm_fun,s_seq,param->flag);
813 if((s_seq=f_pvm_send(0,(char *)0,PVM_EXP_OPT_RESTART_ENCODE2,p_pvm_fun->s_current_tid,p_pvm_fun))==-1) /*automatic increment of seq*/
814 {
815 f_pvm_stop_single_process(*p_merger_tid);
816 if (s_sys_merger_started==1)
817 s_sys_merger_started--;
818 else if (s_sys_merger_started==0)
819 f_pvm_stop_single_process(*p_merger_sys_tid);
820 PVM_CLOSE;
821 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
822 return TC_ERROR;
823 }
824 s_cont=0;
825 }
826 if(param->flag == TC_VIDEO)
827 {
828 p_video_buffer=p_buffer;
829 s_video_seq=s_seq;
830 s_video_cont=s_cont;
831 }
832 else
833 {
834 p_audio_buffer=p_buffer;
835 s_audio_seq=s_seq;
836 s_audio_cont=s_cont;
837 }
838 }
839 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
840 return TC_OK;
841 }
842
843
844 /* ------------------------------------------------------------
845 *
846 * stop codec
847 *
848 * ------------------------------------------------------------*/
849
850 MOD_stop
851 {
852 pvm_func_t *p_pvm_fun=NULL;
853 int *p_merger_tid=0,*p_merger_sys_tid=0;
854 int s_null_module;
855 static int s_msys=0;
856
857 p_merger_sys_tid=(int *)&s_merger_tid_system[0];
858 pthread_mutex_lock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
859 if(param->flag == TC_VIDEO)
860 {
861 s_null_module=s_null_video_module;
862 if (!s_null_module)
863 {
864 p_pvm_fun=&s_pvm_fun_video;
865 p_merger_tid=&s_merger_tid_video[0];
866 }
867 }
868 else
869 {
870 s_null_module=s_null_audio_module;
871 if (!s_null_module)
872 {
873 p_pvm_fun=&s_pvm_fun_audio;
874 p_merger_tid=&s_merger_tid_audio[0];
875 }
876 }
877 if (!s_null_module)
878 {
879 if (p_handle!=NULL)
880 {
881 if (p_pvm_fun!=NULL)
882 {
883 (int)f_pvm_multi_send(0,(char *)0,PVM_EXP_OPT_STOP,p_pvm_fun);
884 f_pvm_stop_single_process(*p_merger_tid);
885 if (s_sys_merger_started!=-1)
886 {
887 if (s_msys==0)
888 {
889 s_msys=1;
890 f_pvm_stop_single_process(*p_merger_sys_tid);
891 memset((char *)&s_pvm_single_proc_system,'\0',sizeof(pvm_func_t));
892 s_merger_tid_system[0]=-1;
893 }
894 }
895 f_pvm_balancer("close",p_pvm_fun,0,param->flag);
896 (pvm_func_t*)f_pvm_master_start_stop("close","tcpvmexportd",(char **)0,p_pvm_conf->s_nproc,p_pvm_conf->s_max_proc,p_pvm_fun);
897 }
898 PVM_DEINIT;
899 if (s_init_check==0)
900 p_handle=NULL;
901 }
902 if(param->flag == TC_VIDEO)
903 {
904 memset((char *)&s_pvm_fun_video,'\0',sizeof(pvm_func_t));
905 s_merger_tid_video[0]=-1;
906 }
907 else
908 {
909 memset((char *)&s_pvm_fun_video,'\0',sizeof(pvm_func_t));
910 s_merger_tid_audio[0]=-1;
911 }
912 }
913 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
914 return TC_OK;
915 }
916
917
918 /* ------------------------------------------------------------
919 *
920 * close codec
921 *
922 * ------------------------------------------------------------*/
923
924 MOD_close
925 {
926 int s_seq=0,s_dummy,s_dummy1,s_rc;
927 pvm_func_t *p_pvm_fun=NULL;
928 int *p_merger_tid=0,*p_merger_sys_tid=0;
929 pvm_func_t *p_pvm_single_proc=NULL;
930 int s_null_module;
931 static int s_msys=0;
932
933 p_merger_sys_tid=(int *)&s_merger_tid_system[0];
934 pthread_mutex_lock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
935 if(param->flag == TC_VIDEO)
936 {
937 s_null_module=s_null_video_module;
938 if (!s_null_module)
939 {
940 p_pvm_fun=&s_pvm_fun_video;
941 p_merger_tid=&s_merger_tid_video[0];
942 p_pvm_single_proc=&s_pvm_single_proc_video;
943 }
944 }
945 else
946 {
947 s_null_module=s_null_audio_module;
948 if (!s_null_module)
949 {
950 p_pvm_fun=&s_pvm_fun_audio;
951 p_merger_tid=&s_merger_tid_audio[0];
952 p_pvm_single_proc=&s_pvm_single_proc_audio;
953 }
954 }
955 if (!s_null_module)
956 {
957 if((s_seq=f_pvm_send(0,(char *)0,PVM_EXP_OPT_RESTART_ENCODE1,p_pvm_fun->s_current_tid,p_pvm_fun))==-1) /*flush the buffer*/
958 {
959 f_pvm_stop_single_process(*p_merger_tid);
960 if (s_sys_merger_started==1)
961 s_sys_merger_started--;
962 else if (s_sys_merger_started==0)
963 f_pvm_stop_single_process(*p_merger_sys_tid);
964 PVM_CLOSE;
965 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
966 return TC_ERROR;
967 }
968 if((f_pvm_multi_send(0,(char *)0,PVM_EXP_OPT_CLOSE,p_pvm_fun))==-1)
969 {
970 f_pvm_stop_single_process(*p_merger_tid);
971 if (s_sys_merger_started==1)
972 s_sys_merger_started--;
973 else if (s_sys_merger_started==0)
974 f_pvm_stop_single_process(*p_merger_sys_tid);
975 PVM_CLOSE;
976 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
977 return TC_ERROR;
978 }
979 if((s_seq=f_pvm_send(0,(char *)0,PVM_JOIN_OPT_RUN,0,p_pvm_single_proc))==-1) /*s_seq not really used*/
980 {
981 f_pvm_stop_single_process(*p_merger_tid);
982 if (s_sys_merger_started==1)
983 s_sys_merger_started--;
984 else if (s_sys_merger_started==0)
985 f_pvm_stop_single_process(*p_merger_sys_tid);
986 PVM_CLOSE;
987 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
988 return TC_ERROR;
989 }
990 if (verbose_flag & TC_DEBUG)
991 {
992 if(param->flag == TC_VIDEO)
993 tc_log_info(MOD_NAME,"Waiting for video merger task (seq %d) termination...",s_seq);
994 else
995 tc_log_info(MOD_NAME,"Waiting for audio merger task (seq %d) termination...",s_seq);
996 }
997 (int)f_pvm_set_recv(s_seq); /*set the last s_seq send*/
998 (int)f_pvm_recv(&s_dummy,(char *)&s_dummy1,&s_rc);
999 if (s_rc)
1000 {
1001 tc_log_warn(MOD_NAME,"Can't close destination file");
1002 f_pvm_stop_single_process(*p_merger_tid);
1003 if (s_sys_merger_started==1)
1004 s_sys_merger_started--;
1005 else if (s_sys_merger_started==0)
1006 f_pvm_stop_single_process(*p_merger_sys_tid);
1007 PVM_CLOSE;
1008 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1009 return TC_ERROR;
1010 }
1011 if (verbose_flag & TC_DEBUG)
1012 tc_log_info(MOD_NAME, "done.");
1013 if (s_sys_merger_started!=-1)
1014 {
1015 if((s_seq=f_pvm_send(0,(char *)0,PVM_JOIN_OPT_SENDFILE,0,p_pvm_single_proc))==-1) /*s_seq not really used*/
1016 {
1017 f_pvm_stop_single_process(*p_merger_tid);
1018 if (s_sys_merger_started==1)
1019 s_sys_merger_started--;
1020 else if (s_sys_merger_started==0)
1021 f_pvm_stop_single_process(*p_merger_sys_tid);
1022 PVM_CLOSE;
1023 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1024 return TC_ERROR;
1025 }
1026 }
1027 if (s_msys)
1028 {
1029 if (verbose_flag & TC_DEBUG)
1030 tc_log_info(MOD_NAME, "Waiting for system merger build list...");
1031 (int)f_pvm_set_recv(PVM_MSG_ENDTASK_SYSTEM); /*wait for system merger end task*/
1032 (int)f_pvm_recv(&s_dummy,(char *)&s_dummy1,&s_rc);
1033 if (verbose_flag & TC_DEBUG)
1034 tc_log_info(MOD_NAME, "done.");
1035 if (s_rc)
1036 {
1037 tc_log_warn(MOD_NAME,"Can't close destination file");
1038 f_pvm_stop_single_process(*p_merger_tid);
1039 PVM_CLOSE;
1040 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1041 return TC_ERROR;
1042 }
1043 if ((p_pvm_conf->s_system_merger.p_hostname!=NULL)&&(p_pvm_conf->s_system_merger.s_build_only_list!=1)) /*do it for 0 and 2*/
1044 {
1045 if((s_seq=f_pvm_send(0,(char *)0,PVM_JOIN_OPT_RUN,0,&s_pvm_single_proc_system))==-1) /*s_seq not really used*/
1046 {
1047 f_pvm_stop_single_process(*p_merger_tid);
1048 f_pvm_stop_single_process(*p_merger_sys_tid);
1049 PVM_CLOSE;
1050 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1051 return TC_ERROR;
1052 }
1053 if (verbose_flag & TC_DEBUG)
1054 tc_log_info(MOD_NAME,"Waiting for system merger task (seq %d) termination...",s_seq);
1055 (int)f_pvm_set_recv(s_seq); /*set the last s_seq send*/
1056 (int)f_pvm_recv(&s_dummy,(char *)&s_dummy1,&s_rc);
1057 if (s_rc)
1058 {
1059 tc_log_warn(MOD_NAME,"Can't close destination file");
1060 f_pvm_stop_single_process(*p_merger_tid);
1061 PVM_CLOSE;
1062 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1063 return TC_ERROR;
1064 }
1065 if (verbose_flag & TC_DEBUG)
1066 tc_log_info(MOD_NAME,"done.");
1067 }
1068 }
1069 if (s_sys_merger_started!=-1)
1070 s_msys=1;
1071 }
1072 pthread_mutex_unlock(&s_channel_lock); /*this is the only way to make my module work with nultithreads: need to change all the code*/
1073 return TC_OK;
1074 }
1075
1076
1077