#include #include #include "aloca.h" #include "sbd.h" #include "sodl.h" #include "longest.h" /* * */ ADD( long operi , long tcand , long *ccand , long *countlist , long *labels , long *label , long *labelled_list , long *which_machine , long *jobpred , long *macpred , long finishing ) { long p1 ; long p2 ; if ((labels[operi] != tcand) && (operi != finishing) ) { p1 = jobpred[operi] ; p2 = macpred[operi] ; if (((labels[p1] == tcand) || (label[p1] != tcand)) && ((labels[p2] == tcand) || (label[p2] != tcand))) { *countlist = *countlist + 1 ; labelled_list[*countlist] = operi ; labels[operi] = tcand ; if (which_machine[operi] == which_machine[tcand]) *ccand = *ccand + 1 ; } } } /* * */ ADD_IN_THE_LIST( long operi , long *countlist , long *labelled , long *labelled_list , long *actrelease , long *releases , long *macpred , long *jobpred , long finishing ) { if (operi != finishing) { if ((labelled[jobpred[operi]] == 1) && (labelled[macpred[operi]] == 1) && (labelled[operi] == 0)) { /* add the operation in the list */ if (releases[operi] < actrelease[operi]) releases[operi] = actrelease[operi] ; *countlist = *countlist + 1 ; labelled_list[*countlist] = operi ; labelled[operi] = 1 ; } } } /* * */ ADD_IN_THE_LIST_1( long opos , long *countlist , long *labelled , long *labelled_list , long *moddeadline , long *processing_time , long *jobsucc , long *macsucc ) { if (opos != 0) { if ((labelled[jobsucc[opos]] == 1) && (labelled[macsucc[opos]] == 1) && (labelled[opos] == 0) ) { /* add the operation in the list */ *countlist = *countlist + 1 ; moddeadline[opos] = MIN(moddeadline[opos], (moddeadline[jobsucc[opos]]-processing_time[jobsucc[opos]])) ; moddeadline[opos] = MIN(moddeadline[opos], (moddeadline[macsucc[opos]]-processing_time[macsucc[opos]])) ; labelled_list[*countlist] = opos ; labelled[opos] = 1 ; } } } long LONGEST_PATH( long m , long my_jobs , long oper , long finishing , long *jobpred , long *jobsucc , long *macpred , long *macsucc , long MKSP_GUESS , long *machine_sched , long *actrelease , long *releases , long *tails , long *moddeadline , long *actdeadline , long *processing_time , long *operations , long *pdc , long *scs , long *LIST , long *POS , long *machine_total , long *labelled_list , long FEASIBILITY_MODE ) { long i , j , pointer ; long pred1 ,succ1 , test_mksp; long finish , countlist , operi , fin , u1 ; long mksp , flag ; long *labelled ; flag = aloci(&labelled,(oper+20)); if (!flag) { printf("Memory problems , longest .... \n") ; exit(1) ;} /* find the releases */ /* initialize */ for (i=0;i<=oper+1;i++) { labelled[i] = 0 ; releases[i] = actrelease[i] ; moddeadline[i] = actdeadline[i] ; if (releases[i] < setup_oper[0][i]) { releases[i] = setup_oper[0][i] ; } pdc[i] = 0 ; } labelled[0] = 1 ; countlist = 0 ; releases[0] = 0 ; processing_time[finishing] = 0 ; processing_time[0] = 0 ; /* start from 0 node and scan all its succesors */ for (i=1;i<=m;i++) { if ( machine_sched[i] == 1) { operi = machine_operations[i][1] ; ADD_IN_THE_LIST(operi, &countlist, labelled, labelled_list, actrelease, releases, macpred, jobpred, finishing) ; } } for (i=1;i<=my_jobs;i++) { operi = job_operations[i][1] ; ADD_IN_THE_LIST(operi, &countlist, labelled, labelled_list, actrelease, releases, macpred, jobpred, finishing) ; } pointer = 0 ; while ( pointer < countlist ) { pointer = pointer + 1 ; /* get an operation from the labelled list */ operi = labelled_list[pointer] ; /* ............ scan it ............ */ succ1 = jobsucc[operi] ; if ( releases[succ1] < releases[operi] + processing_time[operi] +setup_oper[operi][succ1] ) { releases[succ1] = releases[operi] + processing_time[operi] +setup_oper[operi][succ1] ; pdc[succ1] = operi ; } ADD_IN_THE_LIST(succ1, &countlist, labelled, labelled_list, actrelease, releases, macpred, jobpred, finishing) ; succ1 = macsucc[operi] ; if ( releases[succ1] < releases[operi] + processing_time[operi] + setup_oper[operi][succ1]) { releases[succ1] = releases[operi] + processing_time[operi] + setup_oper[operi][succ1] ; pdc[succ1] = operi ; } ADD_IN_THE_LIST(succ1, &countlist, labelled, labelled_list, actrelease, releases, macpred, jobpred, finishing) ; } if ( countlist < oper ) { printf("Cycle *** Oper : %ld , countlist = %ld \n",oper,countlist) ; exit(1) ; } labelled_list[0] = 0 ; labelled_list[oper+1] = finishing ; LIST[0] = 0 ; POS[0] = 0 ; LIST[oper+1] = finishing ; POS[finishing] = oper + 1 ; for (i=0;i<=(oper+1);i++) { LIST[i] = labelled_list[i] ; POS[LIST[i]] = i ; } // printf("MKSP_GUESS = %ld , FEASIBILITY_MODE = %ld \n",MKSP_GUESS , FEASIBILITY_MODE) ; /* find the tails */ /* initialize */ for (i=0;i<=oper+1;i++) { labelled[i] = 0 ; tails[i] = 0 ; if (FEASIBILITY_MODE) { if ((MKSP_GUESS - actdeadline[i]) > 0) { tails[i] = MKSP_GUESS - actdeadline[i] ; } /* modify the tails if you deadlines */ if (tails [ i ] < 0) printf("Smaller than zero \n") ; } scs[i]=finishing; } scs[finishing] = finishing ; labelled[finishing] = 1 ; tails[finishing] = 0 ; countlist = 0 ; /* start from the LAST (n) node and scan all its predecessors */ for (i=1;i<=m;i++){ if ( machine_sched[i] == 1) { operi = machine_operations[i][machine_total[i]] ; ADD_IN_THE_LIST_1(operi, &countlist, labelled, labelled_list, moddeadline, processing_time, jobsucc, macsucc) ; } } for (i=1;i<=my_jobs;i++) { operi = job_operations[i][operations[i]] ; ADD_IN_THE_LIST_1(operi, &countlist, labelled, labelled_list, moddeadline, processing_time, jobsucc, macsucc) ; } pointer = 0 ; while ( pointer < countlist ) { pointer = pointer + 1 ; /* get an operation from the labelled list */ operi = labelled_list[pointer] ; /* ............ scan it ............ */ pred1 = jobpred[operi] ; if ( tails[pred1] < tails[operi] + processing_time[operi] + setup_oper[pred1][operi] ) { tails[pred1] = tails[operi] + processing_time[operi] + setup_oper[pred1][operi] ; scs[pred1] = operi ; } ADD_IN_THE_LIST_1(pred1, &countlist, labelled, labelled_list, moddeadline, processing_time, jobsucc, macsucc) ; pred1 = macpred[operi] ; if ( tails[pred1] < tails[operi] + processing_time[operi] + setup_oper[pred1][operi] ) { tails[pred1] = tails[operi] + processing_time[operi] + setup_oper[pred1][operi] ; scs[pred1] = operi ; } ADD_IN_THE_LIST_1(pred1, &countlist, labelled, labelled_list, moddeadline, processing_time, jobsucc, macsucc) ; } if ( countlist < oper ) { printf("Cycle ... Countlist : %ld \n",countlist) ; exit(1) ; } tails[0] = 0 ; fin = 0 ; for (i=1;i<=oper;i++) { j = i ; if ((tails[j]+processing_time[j]+ releases[j]) >= tails[0] ) { if ((tails[j]+processing_time[j]+ releases[j]) > tails[0] ) { tails[0] = tails[j] + processing_time[j] + releases[j] ; scs[0] = j ; fin = j ; } else { if ((releases[j] < releases[fin]) || (!fin)) { scs[0] = j ; fin = j ; } } } } mksp = 0 ; fin = 0 ; for (i=1;i<=my_jobs;i++) { finish = job_operations[i][operations[i]] ; if (( releases[finish] + processing_time[finish] + tails[finish]) >= mksp ) { if ((releases[finish] + processing_time[finish]+ tails[finish]) > mksp) { mksp = releases[finish] + processing_time[finish] + tails[finish]; pdc[finishing] = finish ; fin = finish ; } else { if ((tails[finish] < tails[fin]) || (!fin)) { fin = finish ; pdc[finishing] = fin ; } } } } if (mksp != tails[0]) printf("1 Error in longest path mksp = %ld , tails0 = %ld\n",mksp,tails[0]) ; u1 = finishing ; /* for (i=1;i<=my_jobs;i++) { for (j=1; j<=operations[i];j++) { finish = job_operations[i][j] ; printf("%ld , release = %ld , tail = %ld , pt = %ld \n", finish, releases[finish],tails[finish],processing_time[finish] ) ; } } printf("tail[0] = %ld , releases[finishing] = %ld \n",tails[0],mksp ) ; */ test_mksp = tails[pdc[finishing]] ; while (u1 != 0) { test_mksp = test_mksp + processing_time[u1] ; test_mksp = test_mksp + setup_oper[pdc[u1]][u1] ; // printf("u1 %ld , pdc[u1] %ld , processing_time[u1] = %ld , setup_oper[pdc[u1]][u1] = %ld\n", // u1,pdc[u1],processing_time[u1],setup_oper[pdc[u1]][u1]) ; scs[pdc[u1]] = u1 ; u1 = pdc[u1] ; } if (test_mksp != mksp) { printf("2 Error in Longest path , test = %ld mksp = %ld , tails[0] %ld\n",test_mksp,mksp,tails[0]) ; printf("pdc[finishing] %ld %ld , tails = %ld %ld %ld\n",pdc[finishing],finishing,tails[pdc[finishing]],processing_time[finishing],setup_oper[pdc[finishing]][finishing]) ; exit(1) ; } free((char *) labelled) ; return(mksp) ; } /* * */ LABEL( long tcand , long i , long *listlen , long *label , long *list , long finishing ) { if ((label[i] != tcand) && (i != finishing)) { *listlen = *listlen + 1 ; label[i] = tcand ; list[*listlen] = i ; } } /* * */ SIMPLE_PATHS( long tcand , long totalcand , long *label , long *labels , long *longes , long *labelled_list , long *processing_time , long *jobsucc , long *macsucc , long *which_machine , long *jobpred , long *macpred , long finishing ) { long pointer ; long succ1 ; long countlist ; long operi ; long ccand ; countlist = 0 ; ccand = 0 ; ADD(tcand, tcand, &ccand, &countlist, labels, label, labelled_list, which_machine, jobpred, macpred, finishing) ; pointer = 0 ; while ( pointer < countlist ) { pointer = pointer + 1 ; operi = labelled_list[pointer] ; succ1 = jobsucc[operi] ; if ( longes[succ1] < longes[operi] + processing_time[operi] + setup_oper[operi][succ1]) longes[succ1] = longes[operi] + processing_time[operi]+ setup_oper[operi][succ1] ; ADD(succ1, tcand, &ccand, &countlist, labels, label, labelled_list, which_machine, jobpred, macpred, finishing) ; succ1 = macsucc[operi]; if ( longes[succ1] < longes[operi] + processing_time[operi] + setup_oper[operi][succ1] ) longes[succ1] = longes[operi] + processing_time[operi] + setup_oper[operi][succ1] ; ADD(succ1, tcand, &ccand, &countlist, labels, label, labelled_list, which_machine, jobpred, macpred, finishing) ; } } /* * CHECK_DEPENDENCIES() */ CHECK_DEPENDENCIES( long machi , long *which_machine , long *processing_time , long *position , long *machine_total , long oper , long *jobsucc , long *macsucc , long finishing , long *labelled_list , long *jobpred , long *macpred ) { long i ; long j ; long i1 ; long i2 ; long tcand ; long cand ; long pointer ; long listlen ; long worth ; long totalcand ; long *longes ; long *label ; long *list ; long *labels ; long flag ; long count_pred ; flag = aloci(&longes,(oper + 2)) * aloci(&label,(oper + 2)) * aloci(&labels,(oper + 2)) * aloci(&list,(oper + 2)) ; count_pred = 0 ; if (!flag) { printf("Memory problems , calculations .... \n") ; exit(1) ;} for (i=1;i<=machine_total[machi];i++) { tpredo[position[machine_operations[machi][i]]] = 0 ; tsucco[position[machine_operations[machi][i]]] = 0 ; for (j=1;j<=machine_total[machi];j++) delay[i][j] = 0 ; } for (j=0;j<=oper+1;j++) { labels[j] = 0 ; label[j] = 0 ; } for (i=1;i<=machine_total[machi];i++) { worth = 0 ; totalcand = 0 ; tcand = machine_operations[machi][i] ; ; list[1] = tcand ; label[tcand] = tcand ; listlen = 1 ; pointer = 0 ; while (pointer < listlen) { pointer = pointer + 1 ; cand = list[pointer] ; longes[cand] = 0 ; if ( which_machine[cand] == which_machine[tcand]) { totalcand = totalcand + 1 ; worth = 1 ; } LABEL(tcand, jobsucc[cand], &listlen, label, list, finishing) ; LABEL(tcand, macsucc[cand], &listlen, label, list, finishing) ; } if (worth) { SIMPLE_PATHS(tcand, totalcand, label, labels, longes, labelled_list, processing_time, jobsucc, macsucc, which_machine, jobpred, macpred, finishing) ; for (j=1;j<=machine_total[machi];j++) { cand = machine_operations[machi][j] ; if ((label[cand] == tcand) && ( longes[cand] > 0)) { i1 = position[tcand] ; i2 = position[cand] ; delay[i1][i2] = longes[cand] ; tpredo[i2] = tpredo[i2] + 1 ; tsucco[i1] = tsucco[i1] + 1 ; predo[i2][tpredo[i2]] = i1 ; succo[i1][tsucco[i1]] = i2 ; } } } } free((char *) longes) ; free((char *) label) ; free((char *) labels) ; free((char *) list) ; } /* * */ long calculations( long m , long my_jobs , long my_first , long my_last , long MKSP_GUESS , long *actrelease , long *actdeadline , long *releases , long *processing_time , long *tails , long *moddeadline , long *pdc , long *scs , long *LIST , long *POS , long *operations , long *macpred , long *macsucc , long *jobpred , long *jobsucc , long finishing , long oper , long FEASIBILITY_MODE ) { long i , j , j1 , j2 , j1j ,j1m ,j2j ,j2m ; long finish , fin , u1 ; long test_mksp , mksp ; /* Update the release and the tails and the new critical path and the reverse critical path */ releases[0] = 0 ; pdc[0] = 0 ; tails[finishing] = 0 ; scs[finishing] = finishing ; moddeadline[finishing] = actdeadline[finishing] ; /* printf("Oper = %ld \n",oper) ; */ for (i=1;i<=oper;i++) { j1 = LIST[i] ; /* * make it equal to the actual release */ releases[j1] = actrelease [ j1 ] ; if (releases[j1] < setup_oper[0][j1]) { releases[j1] = setup_oper[0][j1] ; } pdc[j1] = 0 ; j1j = jobpred[j1] ; j1m = macpred[j1] ; /* printf("%ld %ld \n",j1j,j1m) ; */ if ((releases[j1j]+processing_time[j1j] + setup_oper[j1j][j1]) > (releases[j1m]+processing_time[j1m]+setup_oper[j1m][j1])) { if ((releases[j1j]+processing_time[j1j] +setup_oper[j1j][j1]) > releases [j1]) { releases[j1] = releases[j1j] + processing_time[j1j] + setup_oper[j1j][j1] ; pdc[j1] = j1j ; } } else { if ((releases[j1m]+processing_time[j1m]+setup_oper[j1m][j1]) > releases [j1] ) { releases[j1] = releases[j1m] + processing_time[j1m] +setup_oper[j1m][j1] ; pdc[j1] = j1m ; } } /* printf("Release %ld %ld\n",j1,releases[j1]) ; */ } for (j=oper;j>=1;j--) { j2 = LIST[j] ; tails[j2] = 0 ; if ((FEASIBILITY_MODE) && ((MKSP_GUESS - actdeadline[j2]) > 0)) { tails[j2] = MKSP_GUESS - actdeadline[j2] ; } scs[j2] = finishing ; j2j = jobsucc[j2] ; j2m = macsucc[j2] ; /* printf(" %ld %ld \n",j2j,j2m) ; */ moddeadline[j2] = actdeadline[j2] ; moddeadline[j2] = MIN(moddeadline[j2],(moddeadline[j2j]-processing_time[j2j])) ; moddeadline[j2] = MIN(moddeadline[j2],(moddeadline[j2m]-processing_time[j2m])) ; if (FEASIBILITY_MODE) { if ((tails[j2j] + processing_time[j2j] ) > (tails[j2m] + processing_time[j2m] + setup_oper[j2][j2m])) { if ((tails[j2j]+ processing_time[j2j]) >= tails [ j2 ] ) { tails[j2] = tails[j2j]+ processing_time[j2j] ; scs[j2] = j2j ; } } else { if ((tails[j2m]+ processing_time[j2m] + setup_oper[j2][j2m]) >= tails [ j2 ]) { tails[j2] = tails[j2m]+ processing_time[j2m] + setup_oper[j2][j2m] ; scs[j2] = j2m ; } } } else{ if ((tails[j2j] + processing_time[j2j] ) > (tails[j2m] + processing_time[j2m] + setup_oper[j2][j2m]) ) { tails[j2] = tails[j2j]+ processing_time[j2j] ; scs[j2] = j2j ; } else { tails[j2] = tails[j2m]+ processing_time[j2m] + setup_oper[j2][j2m] ; scs[j2] = j2m ; } } /* printf("Tail %ld , %ld \n",j2,tails[j2]) ; */ } /* update the release time of the finishing operation and its predecessor */ /* update the tail of the starting operation 0 and its successor */ tails[0] = 0 ; fin = 0 ; for (i=1;i<=my_jobs;i++){ j = job_operations[i][1] ; if ((tails[j]+processing_time[j]+releases[j]) >= tails[0] ) { if ((tails[j]+processing_time[j]+releases[j]) > tails[0] ){ tails[0] = tails[j] + processing_time[j] + releases[j] ; scs[0] = j ; fin = j ; } else { if ((releases[j] < releases[fin]) || (!fin)) { scs[0] = j ; fin = j ; } } } } /* calculate the critical path verify its correctness */ /* update the scs and pdc to be consistent */ mksp = 0 ; fin = 0 ; for (i=1;i<=my_jobs;i++) { finish = job_operations[i][operations[i]] ; if (( releases[finish] + processing_time[finish] + tails[finish]) >= mksp ) { if ((releases[finish] + processing_time[finish]+ tails[finish]) > mksp) { mksp = releases[finish] + processing_time[finish] + tails[finish]; pdc[finishing] = finish ; fin = finish ; } else { if ((tails[finish] < tails[fin]) || (!fin)) { fin = finish ; pdc[finishing] = fin ; } } } } releases[finishing] = mksp ; if (releases[finishing] != tails[0]) printf("More r[finishing] %ld t [0] =%ld , MKSP_GUESS = %ld, MODE = %ld \n", releases[finishing],tails[0],MKSP_GUESS,FEASIBILITY_MODE) ; u1 = finishing ; test_mksp = tails[pdc[finishing]] ; while (u1 != 0) { // printf(" pdc[u1] = %ld , u1 = %ld , pt[u1] = %ld , steup = %ld \n", // pdc[u1],u1,processing_time[u1],setup_oper[pdc[u1]][u1] ) ; test_mksp = test_mksp + processing_time[u1] ; test_mksp = test_mksp + setup_oper[pdc[u1]][u1] ; scs[pdc[u1]] = u1 ; u1 = pdc[u1] ; } // printf("test_mksp : %ld\n",test_mksp) ; /*test_mksp = test_mksp + releases[scs[0]] ; */ if (test_mksp != mksp) { printf("Error in the end of calculations() %ld %ld \n",test_mksp,mksp) ; exit(1) ; } return(mksp) ; } /* * */ swift( long AK , long AL , long *LIST , long *POS , long *jobsucc , long *macsucc ) { long NOT_DONE ; long K1 ; long LAMDA ; long GOAL ; long LENGTH_LAMDA ; long flag ; long *AKPH ; long *OLDI_K1 ; flag = aloci(&AKPH,(MAXOPER)) * aloci(&OLDI_K1,(MAXOPER)) ; if (!flag) { printf("Memory problems - swift ... \n") ; exit(1) ; } K1 = POS[AK] ; LAMDA = AK ; GOAL = AL ; LENGTH_LAMDA = 0 ; NOT_DONE = 1 ; while (NOT_DONE) { if (LIST[K1+1] == GOAL ) { if (LAMDA == AK) { LIST[K1] = GOAL ; LIST[K1+1] = LAMDA ; POS[GOAL] = K1 ; POS[LAMDA] = K1 + 1 ; NOT_DONE = 0 ; } else { LIST[K1] = GOAL ; LIST[K1+1] = LAMDA ; POS[GOAL] = K1 ; POS[LAMDA] = K1 + 1 ; LAMDA = AKPH[LENGTH_LAMDA] ; K1 = OLDI_K1[LENGTH_LAMDA] ; LENGTH_LAMDA-- ; } } else { if (LIST[K1+1] == macsucc[LAMDA]) { LENGTH_LAMDA++ ; AKPH[LENGTH_LAMDA] = LIST[K1] ; OLDI_K1[LENGTH_LAMDA] = K1 ; K1++; LAMDA = LIST[K1]; } else { if (LIST[K1+1] != jobsucc[LAMDA]){ LIST[K1] = LIST[K1+1] ; LIST[K1+1] = LAMDA ; POS[LIST[K1]] = K1 ; POS[LIST[K1+1]] = K1 + 1 ; K1++ ; } else { LENGTH_LAMDA++ ; AKPH[LENGTH_LAMDA] = LIST[K1] ; OLDI_K1[LENGTH_LAMDA] = K1 ; K1++; LAMDA = LIST[K1]; } } } } free((char *) AKPH) ; free((char *) OLDI_K1) ; }