Return to BSD News archive
Xref: sserve comp.unix.bsd:3467 comp.protocols.nfs:4191 Newsgroups: comp.unix.bsd,comp.protocols.nfs Path: sserve!manuel!munnari.oz.au!uunet!uunet.ca!shark!latour!mcr From: mcr@Sandelman.OCUnix.on.ca (Michael Richardson) Subject: Das Blinken Lights (sp?) Message-ID: <1992Aug10.074511.11599@Sandelman.OCUnix.on.ca> Organization: Sandelman Software Works, Debugging Department, Ottawa, ON References: <EICHIN.92Aug9004425@tsx-11.mit.edu> <1992Aug9.083431.5746@BitBlocks.COM> Date: Mon, 10 Aug 1992 07:45:11 GMT Lines: 137 One of my favorite things about Sun equipement is the Diagnostic LEDs on the back of the box. (I have a 3/60. I believe all the VME based boxes have the Diag LEDs. I haven't bothered checking any Sparc IPCs). I like it so much I have always put my 3/60 backwards so I can see the LEDs (and it also makes access to the ports easier. It doesn't sit on my desk) I think of them `Cylon' LEDs, although I guess KIT (Knight Rider) might be more familiar to non-Battlestar Galactica watchers. Anyway, have a rediculous number of parallel ports on my 386bsd system, I thought I'd hook something similar up. After bitching at roomate for using all my solder and not buying any more, I finally remembered to pick some up and a friend and I hooked up two last night. Schematic for the curious: D 2 ---w---|>-\ B 3 ---w---|>-+ - 4 ---w---|>-+ 2 5 ---w---|>-+ 5 6 ---w---|>-+ (M) 7 ---w---|>-+ 8 ---w---|>-+ 9 ---w---|>-+ | 25 ----------/ w - 320 ohm resistor |> - LED We hacked an appropriate outb(0x378,blah) call into isa/wd.c to output the low byte of the disk cylinder to the parallel port and watched it the disk seek. Pretty interesting to watch. Almost looks like an sci-fi movie computer! Anyway, after sleeping a bit on where to stick the scanning motion given that the idle task invokes hlt (did I want to pull that instruction out? Having the process halt is actually pretty cool as far as I'm concerned) I came across a solution... Just prior to the hlt instruction I call a C function, moveled. moveled increments a counter each time it is called, and shifts the LED each time the counter hits a value. My pondering was because I figured that I would have to put a large processor delay in there somewhere. The more the idle task ran, the quicker the processor delay would happen. Since the hlt instruction will be interupted at least HZ times a second, this provides a nice way to get a delay without involving the processor, yet counts how often the idle task runs. I had to play with CYLONSPEED a bit to get the timing right. The LEDs are extremely usefull for diagnosing low level boot problems since they are just two instructions. (4 if you have to save edx somewhere in order to load the port address). Oh --- this is all based on 0.0 code since I wasn't able to get 0.1 to boot properly. When my ethernet driver is finished I'll be upgrading via patches. Add i386/isa/cylonled.c optional cylonled to i386/conf/files.i386 and add: options CYLONLED pseudo-device cylonled to your kernel configuration. (If there is a better way to add code, please tell me). We had two LED arrays running on my system, so please change the address appropriately. I'm sure that this could be better done via config(8). Anyway, here is the code: *** /tmp/,RCSt1a11535 Mon Aug 10 03:39:42 1992 --- sys/i386/i386/locore.s Mon Aug 10 03:35:54 1992 *************** *** 924,929 **** --- 940,948 ---- call _spl0 cmpl $0,_whichqs jne sw1 + #ifdef CYLONLED + call _moveled + #endif /* CYLONLED */ hlt # wait for interrupt jmp idle *** /dev/null Mon Aug 10 03:40:04 1992 --- sys/i386/isa/cylonled.c Sun Aug 9 17:57:34 1992 *************** *** 0 **** --- 1,42 ---- + #include "sys/param.h" + #include "sys/proc.h" + #include "sys/user.h" + #include "sys/systm.h" + + #define CYLONLEDLOC 0x378 + #define CYLONLEDLOC1 0x3BC + #ifndef CYLONSPEED + #define CYLONSPEED 5 + #endif + + int cylonledspeed=CYLONSPEED; + + void moveled() + { + static int count=0; + static unsigned int ledval=1; + static int dir=0; + + + if(count++>cylonledspeed) { + count=0; + + if(dir) { + ledval=ledval>>1; + if(ledval==0x01) { + dir=0; + } + } else { + ledval=ledval<<1; + if(ledval==0x80) { + dir=1; + } + } + /* if(ledval==0) { + printf("Led fucked!\n"); + }*/ + } + outb(CYLONLEDLOC,ledval); + outb(CYLONLEDLOC1,ledval); + } + -- :!mcr!: | The postmaster never | So much mail, Michael Richardson | resolves twice. | so little time. HOME: mcr@sandelman.ocunix.on.ca Bell: (613) 237-5629 SCHOOL: 192228@physics.carleton.ca