00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #include<linux/sched.h>
00012 #include<asm/bitops.h>
00013 #include<ssdef.h>
00014 #include<cebdef.h>
00015 #include<evtdef.h>
00016 #include<ipldef.h>
00017 #include<system_data_cells.h>
00018 #include<ipl.h>
00019 #include<internals.h>
00020 #include <exe_routines.h>
00021 #include <sch_routines.h>
00022 #include <misc_routines.h>
00023
00024 #undef MYDEB_EFC
00025 #define MYDEB_EFC
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 int waitcheck(struct _pcb *p, unsigned long priclass, unsigned long * efp, unsigned long * clusteraddr) {
00037 unsigned long tmp;
00038 if (efp!=clusteraddr) return;
00039 tmp=(*clusteraddr)&~p->pcb_l_efwm;
00040 #if 0
00041 *clusteraddr&=~p->pcb_l_efwm;
00042 #endif
00043 if (!tmp) return;
00044
00045
00046
00047 sch_rse(p,priclass,EVT$_EVENT);
00048 }
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059 int waitcheck2(struct _pcb *p, unsigned long priclass, unsigned long * efp, unsigned long * clusteraddr) {
00060 unsigned long tmp;
00061
00062 tmp=(*clusteraddr)&~p->pcb_l_efwm;
00063
00064 if (tmp==0) return;
00065 if (p->pcb_l_sts&PCB$M_WALL) {
00066 if (p->pcb_l_efwm!=(~tmp))
00067 return;
00068 }
00069
00070
00071 sch_rse(p,priclass,EVT$_EVENT);
00072 }
00073
00074 #ifdef MYDEB_EFC
00075 long efc[32*1024];
00076 long efcc[32] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
00077 #endif
00078
00079
00080
00081
00082
00083
00084
00085
00086 int sch_postef(unsigned long ipid, unsigned long priclass, unsigned long efn) {
00087
00088 int savipl=vmslock(&SPIN_SCHED,IPL__SYNCH);
00089 #ifdef MYDEB_EFC
00090 {
00091 int pid=ipid&31;
00092 efc[1024*pid+efcc[pid]]=efn;
00093 efcc[pid]++;
00094 long addr = &ipid;
00095 addr-=4;
00096 efc[1024*pid+efcc[pid]]=*(long*)addr;
00097 efcc[pid]++;
00098 if (efcc[pid]>1000)
00099 efcc[pid]=0;
00100 }
00101 #endif
00102 struct _pcb * p, * first;
00103 int efncluster=getefcno(efn);
00104 int retval;
00105 unsigned long * clusteraddr;
00106
00107 p=exe_ipid_to_pcb(ipid);
00108
00109 if (!p) {
00110 retval = SS__NONEXPR;
00111 goto end;
00112 }
00113
00114 if (efn>127) {
00115 retval = SS__ILLEFC;
00116 goto end;
00117 }
00118 clusteraddr=getefc(p,efn);
00119
00120
00121 if (efncluster<2) {
00122 if (test_and_set_bit(efn&31,clusteraddr))
00123 retval=SS__WASSET;
00124 else
00125 retval=SS__WASCLR;
00126
00127 waitcheck(p,priclass,&p->pcb_l_efcs+p->pcb$b_wefc,clusteraddr);
00128 } else {
00129
00130 struct _ceb * c=*(unsigned long *)getefcp(p,efn);
00131 struct _pcb * tmp, *next;
00132 if (!c) {
00133 retval=SS__UNASEFC;
00134 goto end;
00135 }
00136
00137 if (test_and_set_bit(efn&31,clusteraddr))
00138 retval=SS__WASSET;
00139 else
00140 retval=SS__WASCLR;
00141
00142
00143 if (retval==SS__WASCLR) {
00144 first=&c->ceb_l_wqfl;
00145 tmp=first->pcb_l_sqfl;
00146 while (first!=tmp) {
00147 clusteraddr=getefc(tmp,efn);
00148 next=tmp->pcb_l_sqfl;
00149
00150 waitcheck2(tmp,priclass,&tmp->pcb_l_efcs+tmp->pcb$b_wefc,clusteraddr);
00151 tmp=next;
00152 }
00153 }
00154 }
00155 end:
00156
00157 vmsunlock(&SPIN_SCHED,savipl);
00158 return retval;
00159 }
00160