/* lunattach.c - manage LUNs for DECUS C RSX11M+ */ #include #include #define local #ifdef DOCUMENTATION title Lunattach Logical Unit Number control index LUN index Lunattach index Logical Unit Number index Attatchment of LUN usage int lun; /* -ve IE_??? error code or +ve LUN */ char * devstr; /* typically "DDnnn" */ lun = lunattach(devstr); description Assign, then attach, a LUN (previously not in use by your task) to the device named in devstr. Devstr does not require ':'. Beware that a device name with node name will be misinterpreted viz. "MYNODE::LB42:MUMBLE.UPU;6" will be interpreted as device MY0: because the rules are: first two characters are device name and any characters starting at third character that can be interpreted as an octal number form the device number. Return the LUN number (positive) if we suceeded. This means that we could assign the LUN to the device and also attach it. Return an RSX error code if we failed. Return IE.ULN (Unassigned LUN) if we had no available LUNs for this task, right now. Unfortunately the only way we can detect a free LUN is if the LUN is attached. Mere LUN assignment to a legal device is not easily detectable, and it appears hard to "unassign" a LUN. So after lunassign() gives you a LUN, IO.ATT it to dedicate the LUN and IO.DET it to free it for another lunassign(). internal Distinguish two ideas: (1) how we determine a LUN is eligible for assignment; (2) which order we try to assign LUNs. A LUN is available if and only if it is not attached. So if you want to re-use a LUN please IO.DET the LUN. We find a free LUN by trying every LUN (highest to lowest) until we find one that RSX will accept. This is crude but works. If you have a better way to assign LUNs without annoying other people's run-time systems, please submit it to DECUS. bugs This is for RSX only. May later evolve for VMS, RSTS, RT, XXDP, UNIX, DOS etc. Lets make it understand node names one day, and skip past them to the device name, or even get the right device at the right node assigned to the lun. #endif extern int _nluns; /* RSX11M taskbuilder: LUNs are [1:(.nluns)] */ int lunattach (devstr) char * devstr; /* string defining device */ /* for RSX: we expect exactly 2 letters, then */ /* an OCTAL unit number. */ BEGIN /* * We expect to use RSX error codes if the device string is ill * conditioned. So we assume it is OK and RSX detects all the * bad news. */ int devnam; int devunt; int lun; int junk[6]; /* 6 is magic number of words returned */ char result; copy(&devnam,devstr,2); devunt = 0; /* assume 0 if sscanf fails */ sscanf(devstr+2,"%o",&devunt); FOR (lun=_nluns; lun; lun--) DO IF ((glun(lun,junk)&0xFF)==IE_ULN) THEN /* we have a usable lun */ IF (alun(lun,devnam,devunt)==IS_SUC) THEN return(lun); FI FI OD result = IE_ULN; /* sign extend so it really is -ve */ return(result); /* no LUNs available - caller loses */ END /* end: lun.c */