Toastie Posted February 1, 2023 Author Posted February 1, 2023 (edited) 16 hours ago, Toastie said: Interestingly, exactly this behavior is replicated in DOSBox-X. A hiccup occurs every 24 ms, as per measurement. Which makes me believe, DOSBox-X simulates a 8520 UART for the serial port. You can choose a Pentium processor - but I believe the serial port behavior remains identical. Can further support this speculation: My Satellite 4090 laptop (I believe @alexGS is also using, correct Alex?), a 16550 equivalent UART is doing the serial communication. That one handles baud rates > 9600 and has serial I/O buffers: https://www.minuszerodegrees.net/manuals/Toshiba/Satellite/Toshiba Satellite 4090XCDT - Product Specifications.pdf On this computer, TCLogo_s works absolutely fine within margin of error using 19200 baud for the serial communication with the Arduino. There is some very minor jitter, I can't even quantify on my scope. But there is no hiccup at all. I may have a look at my 5 lines of Arduino c++ code, but that seems to be fine. Just as a test: 38400 baud work as well - this gives more time to do other things on the Arduino, if desired :D (when not wanting to use interrupts, that is). There is of course no real reason to run the serial TCLogo version Alex made on this particular machine, as the 4090 has a parallel port as well, and thus TCLogo_p runs perfectly well. However, it is always good to know what causes which jitter or hiccup ;) on home brew stuff made by an amateur. Conclusion: The slightly off timing at 9600 baud in DOSBox-X is due to the 8250 UART simulation. The hiccup (= 1 ms wrong output after 24 ms) is due to the 9600 baud. The weird behavior at 19200 baud in DOSBox-X (timing becomes simulated processor dependent) is a simulation artifact, mostly caused by the 8250 simulation, I believe. Best regards, Thorsten Edited February 1, 2023 by Toastie Quote
Toastie Posted February 1, 2023 Author Posted February 1, 2023 (edited) So I heard my group was just awarded with a major EU program fund - this needs some attention from my side :D It is within a consortium of some chip manufacturers, research institutions and universities, all playing around with EUV light and such things ... So just FYI - here is the 5 line c++ code (plus a lot of text, so I still may understand what I did. Tend to forget such things after a couple of days ...) Few remarks: The LED illumination is entirely optional, as 9750 has its own LEDs. It was just for me during programming as quick visual feedback. I am a BASIC person. For me, C++ is like coming from outer space and I have to look up nearly everything - and over and over again ... In other words, this reduces the "code" to 4 lines w/o the remarks and definitions :D I am using direct port manipulation only (which is NOT recommended by the Arduino folks, as this is of course board/microcontroller specific. But I find it cool. Also, all bits are changed >simultaneously< as the register content is thrown onto the outputs in essentially one instruction step. I like that. 6 x digitalWrite is not cool :D. It is more an homage to the 9771 card and 9771/9750 communication The traditional way of I/O pin handling is thus commented out and just for me to remember. All that is needed is either an Arduino Nano or Uno (watch the pinout, microcontrollers have identical port descriptors), I have tested both; a serial2TTL converter just running in parallel to the TX/RX lines of the Arduino. For programming, only the RX line of the converter needs to be temporarily disconnected, as otherwise the Arduino can't listen to the USB port. This is why I installed a little switch, see page 1 of this thread. I bet there is a much more elegant way to manipulate the ports in c++ using &|<>!^ ... But: It works. // //Serial Interface for TCLogo to 9750 parallel input/output //Uses port manipulation: https://playground.arduino.cc/Learning/PortManipulation/ // //Port commands: DDRX : port direction of port X; 0=in, 1=out // PORTX : write to port X // PINX : read port X (also to read back output status //Works on Arduino Uno R3 and //Arduino Nano using the "Processor: ATmega328P/old bootloader" option in menu Tools /* Traditional pin definition setup #define bit0_output 2 // 9750 output 0 #define bit1_output 3 // 1 #define bit2_output 4 // 2 #define bit3_output 5 // 3 #define bit4_output 6 // 4 #define bit5_output 7 // 5 #define bit6_input 8 // 9750 input 6 #define bit7_input 9 // 7 */ void setup() { // Init IO pins ---------------------------------------------------------------------------------------------- /* Traditional I/O setup pinMode (bit0_output, OUTPUT); pinMode (bit1_output, OUTPUT); pinMode (bit2_output, OUTPUT); pinMode (bit3_output, OUTPUT); pinMode (bit4_output, OUTPUT); pinMode (bit5_output, OUTPUT); pinMode (bit6_input, INPUT); pinMode (bit7_input, INPUT); */ pinMode (8, INPUT_PULLUP); // Pullup needs to be defined >before< port direction settings pinMode (9, INPUT_PULLUP); // This mimics the behavior of the 9750 sensor ports: Open = true //Port configuration for Arduino; see above Arduino reference link // pins 76543210 // port D 765432XX // TCLogo 543210 // 9750 543210 DDRD = DDRD | B11111100; // Port D direction setting 1 = output; 0 input. // This is safe: It sets pins 2 to 7 as outputs // without changing the mode of pins 0 & 1 (RX/TX) // pins XXX21098 // Port B: Ports 5-7; pins 13-15 not usable on Nano // port B XX543210 // DDRB |= B00001100; // Ports B2/B3 = outputs, all other unchanged (B5-7 not usable). DDRB &= B11111100; // Ports B0/B1 = inputs, all other unchanged. // Init serial ports ----------------------------------------------------------------------------------------- Serial.begin(19200); // Init hardware serial port (pins 0+1) // Notes: 9600 baud is the native QBasic maximum as well as the // maximum on the IBM XT. // 19200 baud work when reprogamming the UART using DEBUG within // DOSBox-X (although not fully) and on the Toshiba 4090. // 38400 baud work (only) on the 4090 as well // using DOSBox-x while (!Serial) {} // Wait for serial port to connect } // end setup ------------------------------------------------------------------------------------------------- void loop() { //------------------------------------------------------------------------------------------------ uint8_t newPINB; // For temporal storage of port B status. newPINB = PINB & B00000011; // Read port B, lower 2 bits (=> sensors 6+7 on 9750). // Need to use a variable for temporal storage of port B status: // PORTB |= ((PINB & B00000011) << 2) does not work. //PORTB |= (newPINB << 2); // CRAP, DOES ONLY WORK ONCE!!! The LEDs simply stay ON. PORTB = newPINB <<2 // Much better: LEDs on port B 3+4 showing the sensor status (optional). if (Serial.available()){ // Something arrived at the serial port = TCLogo_s write // -> no error checking! PORTD = Serial.read() << 2; // Arduino output port LEDs (0-5 on 9750 = PORTD 3-8). Optional. Serial.write(((PIND & B11111100) >> 2) | (newPINB << 6)); // Reply to TCLogo_s: // Read the output status, shift right by 2 = bits 0-5. // Add bits 6+7 by shifting the port B input bits left by 6 } }//void loop --------------------------------------------------------------------------------------------------- Best wishes, Thorsten AND EDITED AGAIN - oh my. Don't code in C++ if you are a BASIC person ... the line: PORTB |= (newPINB) << 2); works exactly once when an input on 9750 goes low - after that no changes occur on the IN LEDs anymore; they simply stay on. The code needs to be PORTB = newPINB << 2. I am very sorry - change that above as well. Edited May 18, 2023 by Toastie C++ code Quote
evank Posted March 20, 2023 Posted March 20, 2023 Does anyone have a scan of the original instructions for connecting a BBC Micro (B, B+, Master) to Interface A? I know it's just the 20-pin ribbon cable, but I am curious to see how Lego documented it for BBC computers. I have the Apple II, Commodore 64, and IBM PC instructions. Quote
Toastie Posted March 22, 2023 Author Posted March 22, 2023 On 3/20/2023 at 1:32 AM, evank said: I know it's just the 20-pin ribbon cable, but I am curious to see how Lego documented it for BBC computers. Hi Evan, is/was there any impetus to reach out to TLG on these issues? I bet there are/were - I am a "bit" late to the game. All the best, Thorsten Quote
evank Posted March 27, 2023 Posted March 27, 2023 I'm skeptical that they would help, but I left a message through their web chat system. Quote
Toastie Posted March 27, 2023 Author Posted March 27, 2023 Hi Evan, this is certainly not what you are looking for, but maybe you get some info you are looking for. Daniel Schmatz (from Austria) who is operating a "museum for pinball machines and LEGO sets" near Vienna/Austria ("eitle Kinderkram", this is the webpage: https://kinderkram.eitle.at/), made a YouTube video in 2021 "showing" all pages of the booklets that came along with 1455 in 1986. The video quality is really not that good, but as said, almost all pages are shown. I accidentally ran across this website when I tried to understand what 9771 is and does, as you know regarding TC, I started from scratch in late 2022. Daniel has a >very< impressive collection of LEGO sets including Technic/Dacta - and has also the Apple II and IBM PC cards. Not sure about the C64 cable only connection, though. The video is 2 years old, that may have changed, but it is nice to see how surprised he is in the video, that the BBC does not need an interface card: About 11 minutes into the video, the hardware setup is shown, and he really takes some time to comprehend the setup (fingers running across the BBC, the disk station, interface A - but no interface card, and gets excited about it. So just have a look and enjoy the nice Austrian accent of his German :D All the best, Thorsten Quote
evank Posted April 3, 2023 Posted April 3, 2023 (edited) Thanks @Toastie I will check out the video. >> has also the Apple II and IBM PC cards. Not sure about the C64 cable only connection I have all three of those. :) Update: I watched the video, and that's definitely what I need! I emailed him just now. Thanks again for the tip. Edited April 3, 2023 by evank Quote
Toastie Posted April 3, 2023 Author Posted April 3, 2023 (edited) 2 hours ago, evank said: I have all three of those. :) I know :) You wrote it - and that is so unbelievably cool! Well, my youth never ran into the C64, it was Sinclair world ... But I found one C64 with floppy drive in the storage room of my resarch group. I joined the University of Wuppertal in 2001 as chair of the Physical Chemistry group. In 2010, we merged PChem and Theoretical Chem (TC) into PTC. My predecessors joined in 1974 - 1980; and since then, it appears as if - no - things have piled up . My colleagues are all "gone" - either left Earth (2) or are retired (2). And new colleagues (not me) hired recently don't ... want to deal with 1980s - 1990s crap. That is why there are still (1) C64, (3) Ataries (1024) with three 30MByte HD drives, and "my" IBM XT ... and much more in electronic stuff, even Germanium transistors (the "AC" series and the like :D). So, I guess - I should make a ZX Spectrum fit for operating interface A - all it needs is a cable . And yes, the connectors to the backplane of the Speccy are in the basement as well. It was a small world, back then, in the 1980s. OK, I need to make a program as well. But my love for the Speccy never faded, so it will be fun to do so. 2 hours ago, evank said: I emailed him just now. How cool is that!!! Hope he replies! And - one day - there may be scans of these booklets on the Internet Archive. All the best, Thorsten Edited April 3, 2023 by Toastie Quote
Toastie Posted May 19, 2023 Author Posted May 19, 2023 (edited) Long time, no necro-bump … Little update: Looked into TCLogo assembly code, as @alexGS has already done. Alex chased the occurrence(s) of the addresses used in the TCLogo I/O routines writing to and reading from the LEGO #9774 PC ISA card (either 39Dh/925d or 39Eh/926d, depending on address bridge presence on the PCB; out/in) in order to change them to parallel port addresses (TCLogo_p.com, 378h/888d out; 379h/889d in) or serial port addresses (TCLogo_s.com, 3F8h/1016d; out/in), so that semi-vintage computers lacking vintage ISA bus support can natively run the respective TCLogo version. He succeeded and has hacked and provided these TCLogo variants on his Bricksafe folder (https://bricksafe.com/pages/alexGSofNZ/interface-a-tc-logo). My interest focuses on the PWM pulses present on the 6 outputs of the LEGO interface A box #9750. As per oscilloscope measurements it became clear that each power setting in TCLogo (0-7; 0 = off, 7 = on, all other = PWM) is changing its output status from 0 to 1 with 1 ms temporal resolution. The thing is: independent of computer used, be it an original IBM XT or a Toshiba laptop – even in the DOSBox-X emulator running TCLogo_s on a i7/Win11 laptop. This strongly suggested the presence of a hardware interrupt routine to be responsible for this behavior – at least under MSDOS, regardless of DOS version. Executive summary: When starting up, TCLogo 1) changes partly the DOS interrupt vector table content 2) changes the time base of the programmable interrupt timer to 1 ms 3) hooks int 8 = IRQ 0 (timer interrupt) for 1ms PWM output 4) chains from int 8 to int 95 (which points to the original int 8 vector) every 55 times, int 8 is executed, to maintain the correct system time. My ultimate goal is to use this approach in combination with QuickBasic 4.5, so that PWM control becomes available as well in this programming environment (I am struggling with TCLogo’s programming logic …) – I am a BASIC person. QuickBasic 4.5 is also from the olden days, when 4.5V LEGO Technic Control was around, i.e, from the mid to late 1980ies. In more detail: For the analysis of TCLogo, Alex suggested to do that with the DOSBox-X debugger, as the assembly code of TCLogo swiftly becomes hard to trace using a disassembler. I first tried a disassembler as well; however when an assembly program begins with a relative rather long “jmp“ and then does a few things like producing the splash screen and then just waits for the user to hit return, things get a bit messy right away as you need to follow the jump targets – everything in between may just be – something, data, whatever – but not assembly code instructions. The free version of IDA Pro dissembler (5.0 from 2010) is a) disassembling 8086 assembly very well and b) does analyze the assembly code by tracing jumps. Nevertheless, after asking for the “return” key it is over as well. Particularly as TCLogo does what apparently was done back in the days, when games or other nifty programs needed to be fast: It changes some of the DOS interrupt vector table content, then manipulates the programmable system timer (PIT) and then hooks some of the new interrupt vectors. Then it does some house-keeping, produces the splash screen, and finally waits for the user to press “return”. This made it rather tough to produce any reasonable disassembler output even with IDA. This is entirely due to my limited capabilities, of course, I bet, IDA tells you everything when you know how to use it properly. Even worse, in the beginning I had no clue what “segment” and “offset” meant. My assembly world was so far limited to 64k computers = linear address space. It took me a while to figure out how this works … also the register operations of the 8086 seemed to be odd sometimes … very steep learning curve – and that still remains so. So I followed (again) Alex’ advice and used the debugger of DOSBox-X, as said, to log/read the code, TCLogo actually executes. The log file also contains all register content and so on. The debugger can also list the DOS interrupt table content – this way I figured out what changed after TCLogo is running. And sure enough, among others, the DOS interrupt vector 8 (hardware IRQ 0 = timer interrupt) is not pointing to BIOS anymore, but to TCLogo code. Somewhere else in the manipulated vector table the original interrupt 8 vector is stored. The two tables are listed in the spoilers below. Spoiler 1: Interrupt table DOS only (warning: 256 lines long) Spoiler INT 00: F000:CA60 INT 01: 0070:00F4 INT 02: 0070:00F4 INT 03: 0070:00F4 INT 04: 0070:00F4 INT 05: F000:FF54 INT 06: F000:CA60 INT 07: F000:CA60 INT 08: F000:FEA5 INT 09: F000:E987 INT 0A: F000:FF55 INT 0B: F000:CE80 INT 0C: F000:CE80 INT 0D: F000:CE80 INT 0E: F000:CCE0 INT 0F: 0070:00F4 INT 10: C000:00EE INT 11: F000:CB20 INT 12: F000:CB40 INT 13: F000:CF60 INT 14: F000:CB80 INT 15: F000:CBA0 INT 16: F000:CFC0 INT 17: F000:CBC0 INT 18: F000:CD00 INT 19: F000:CC60 INT 1A: F000:CBE0 INT 1B: F000:D1C0 INT 1C: F000:CC00 INT 1D: F000:C958 INT 1E: F000:CA60 INT 1F: C000:05E9 INT 20: F000:D0E0 INT 21: F000:D100 INT 22: F000:DAC8 INT 23: 072F:0000 INT 24: 072F:0110 INT 25: F000:D120 INT 26: F000:D140 INT 27: F000:D160 INT 28: F000:D180 INT 29: F000:D1A0 INT 2A: F000:D240 INT 2B: F000:CA60 INT 2C: F000:CA60 INT 2D: F000:CA60 INT 2E: 072F:0118 INT 2F: F000:D220 INT 30: 00D1:E0EA INT 31: F000:CAF0 INT 32: F000:CA60 INT 33: C402:0010 INT 34: F000:CA60 INT 35: F000:CA60 INT 36: F000:CA60 INT 37: F000:CA60 INT 38: F000:CA60 INT 39: F000:CA60 INT 3A: F000:CA60 INT 3B: F000:CA60 INT 3C: F000:CA60 INT 3D: F000:CA60 INT 3E: F000:CA60 INT 3F: F000:CA60 INT 40: F000:CA60 INT 41: F000:CF80 INT 42: F000:CA60 INT 43: C000:01E9 INT 44: F000:CA60 INT 45: F000:CA60 INT 46: F000:CFA0 INT 47: F000:CA60 INT 48: F000:CA60 INT 49: F000:CA60 INT 4A: F000:CA60 INT 4B: F000:D280 INT 4C: F000:CA60 INT 4D: F000:CA60 INT 4E: F000:CA60 INT 4F: F000:CA60 INT 50: F000:CA60 INT 51: F000:CA60 INT 52: F000:CA60 INT 53: F000:CA60 INT 54: F000:CA60 INT 55: F000:CA60 INT 56: F000:CA60 INT 57: F000:CA60 INT 58: F000:CA60 INT 59: F000:CA60 INT 5A: F000:CA60 INT 5B: F000:CA60 INT 5C: F000:CA60 INT 5D: F000:CA60 INT 5E: F000:CA60 INT 5F: F000:CA60 INT 60: 0000:0000 INT 61: 0000:0000 INT 62: 0000:0000 INT 63: 0000:0000 INT 64: 0000:0000 INT 65: 0000:0000 INT 66: F000:CA60 INT 67: C401:0004 INT 68: F000:CA60 INT 69: F000:CA60 INT 6A: F000:CA60 INT 6B: F000:CA60 INT 6C: F000:CA60 INT 6D: F000:CA60 INT 6E: F000:CA60 INT 6F: F000:CA60 INT 70: F000:CC20 INT 71: F000:CC40 INT 72: F000:CE80 INT 73: F000:CE80 INT 74: F000:D020 INT 75: 0000:0000 INT 76: F000:CCA0 INT 77: F000:CCC0 INT 78: 0000:0000 INT 79: 0000:0000 INT 7A: 0000:0000 INT 7B: 0000:0000 INT 7C: 0000:0000 INT 7D: 0000:0000 INT 7E: 0000:0000 INT 7F: 0000:0000 INT 80: 0000:0000 INT 81: 0000:0000 INT 82: 0000:0000 INT 83: 0000:0000 INT 84: 0000:0000 INT 85: 0000:0000 INT 86: 0000:0000 INT 87: 0000:0000 INT 88: 0000:0000 INT 89: 0000:0000 INT 8A: 0000:0000 INT 8B: 0000:0000 INT 8C: 0000:0000 INT 8D: 0000:0000 INT 8E: 0000:0000 INT 8F: 0000:0000 INT 90: 0000:0000 INT 91: 0000:0000 INT 92: 0000:0000 INT 93: 0000:0000 INT 94: 0000:0000 INT 95: 0000:0000 INT 96: 0000:0000 INT 97: 0000:0000 INT 98: 0000:0000 INT 99: 0000:0000 INT 9A: 0000:0000 INT 9B: 0000:0000 INT 9C: 0000:0000 INT 9D: 0000:0000 INT 9E: 0000:0000 INT 9F: 0000:0000 INT A0: 0000:0000 INT A1: 0000:0000 INT A2: 0000:0000 INT A3: 0000:0000 INT A4: 0000:0000 INT A5: 0000:0000 INT A6: 0000:0000 INT A7: 0000:0000 INT A8: 0000:0000 INT A9: 0000:0000 INT AA: 0000:0000 INT AB: 0000:0000 INT AC: 0000:0000 INT AD: 0000:0000 INT AE: 0000:0000 INT AF: 0000:0000 INT B0: 0000:0000 INT B1: 0000:0000 INT B2: 0000:0000 INT B3: 0000:0000 INT B4: 0000:0000 INT B5: 0000:0000 INT B6: 0000:0000 INT B7: 0000:0000 INT B8: 0000:0000 INT B9: 0000:0000 INT BA: 0000:0000 INT BB: 0000:0000 INT BC: 0000:0000 INT BD: 0000:0000 INT BE: 0000:0000 INT BF: 0000:0000 INT C0: 0000:0000 INT C1: 0000:0000 INT C2: 0000:0000 INT C3: 0000:0000 INT C4: 0000:0000 INT C5: 0000:0000 INT C6: 0000:0000 INT C7: 0000:0000 INT C8: 0000:0000 INT C9: 0000:0000 INT CA: 0000:0000 INT CB: 0000:0000 INT CC: 0000:0000 INT CD: 0000:0000 INT CE: 0000:0000 INT CF: 0000:0000 INT D0: 0000:0000 INT D1: 0000:0000 INT D2: 0000:0000 INT D3: 0000:0000 INT D4: 0000:0000 INT D5: 0000:0000 INT D6: 0000:0000 INT D7: 0000:0000 INT D8: 0000:0000 INT D9: 0000:0000 INT DA: 0000:0000 INT DB: 0000:0000 INT DC: 0000:0000 INT DD: 0000:0000 INT DE: 0000:0000 INT DF: 0000:0000 INT E0: 0000:0000 INT E1: 0000:0000 INT E2: 0000:0000 INT E3: 0000:0000 INT E4: 0000:0000 INT E5: 0000:0000 INT E6: 0000:0000 INT E7: 0000:0000 INT E8: 0000:0000 INT E9: 0000:0000 INT EA: 0000:0000 INT EB: 0000:0000 INT EC: 0000:0000 INT ED: 0000:0000 INT EE: 0000:0000 INT EF: 0000:0000 INT F0: 0000:0000 INT F1: 0000:0000 INT F2: 0000:0000 INT F3: 0000:0000 INT F4: 0000:0000 INT F5: 0000:0000 INT F6: 0000:0000 INT F7: 0000:0000 INT F8: 0000:0000 INT F9: 0000:0000 INT FA: 0000:0000 INT FB: 0000:0000 INT FC: 0000:0000 INT FD: 0000:0000 INT FE: 0000:0000 INT FF: 0000:0000 Spoiler 2: Interrupt table DOS + TCLogo_s running (warning: 256 lines long) Spoiler INT 00: F000:CA60 INT 01: 0070:00F4 INT 02: 0070:00F4 INT 03: 0070:00F4 INT 04: 0070:00F4 INT 05: 1481:04CE ; TCLogo code; DOS: Print Screen key INT 06: F000:CA60 INT 07: F000:CA60 INT 08: 1481:0365 ; TCLogo code; DOS: Timer interrupt (was F000:FEA5 -> Int 95 has this vector w/ TCLogo) INT 09: F000:E987 INT 0A: F000:FF55 INT 0B: F000:CE80 INT 0C: F000:CE80 INT 0D: F000:CE80 INT 0E: F000:CCE0 INT 0F: 0070:00F4 INT 10: C000:00EE INT 11: F000:CB20 INT 12: F000:CB40 INT 13: F000:CF60 INT 14: F000:CB80 INT 15: F000:CBA0 INT 16: F000:CFC0 INT 17: F000:CBC0 INT 18: F000:CD00 INT 19: F000:CC60 INT 1A: F000:CBE0 INT 1B: 1481:04CE ; TCLogo code; DOS: CTRL BREAK key - same as INT 05 INT 1C: F000:CC00 INT 1D: F000:C958 INT 1E: F000:CA60 INT 1F: C000:05E9 INT 20: F000:D0E0 INT 21: F000:D100 INT 22: F000:DAC8 INT 23: 072F:0000 INT 24: 0A64:02E4 ; TCLogo code; DOS: FATAL ERROR handler INT 25: F000:D120 INT 26: F000:D140 INT 27: F000:D160 INT 28: F000:D180 INT 29: F000:D1A0 INT 2A: F000:D240 INT 2B: F000:CA60 INT 2C: F000:CA60 INT 2D: F000:CA60 INT 2E: 072F:0118 INT 2F: F000:D220 INT 30: 00D1:E0EA INT 31: F000:CAF0 INT 32: F000:CA60 INT 33: C402:0010 INT 34: F000:CA60 INT 35: F000:CA60 INT 36: F000:CA60 INT 37: F000:CA60 INT 38: F000:CA60 INT 39: F000:CA60 INT 3A: F000:CA60 INT 3B: F000:CA60 INT 3C: F000:CA60 INT 3D: F000:CA60 INT 3E: F000:CA60 INT 3F: F000:CA60 INT 40: F000:CA60 INT 41: F000:CF80 INT 42: F000:CA60 INT 43: C000:01E9 INT 44: F000:CA60 INT 45: F000:CA60 INT 46: F000:CFA0 INT 47: F000:CA60 INT 48: F000:CA60 INT 49: F000:CA60 INT 4A: F000:CA60 INT 4B: F000:D280 INT 4C: F000:CA60 INT 4D: F000:CA60 INT 4E: F000:CA60 INT 4F: F000:CA60 INT 50: F000:CA60 INT 51: F000:CA60 INT 52: F000:CA60 INT 53: F000:CA60 INT 54: F000:CA60 INT 55: F000:CA60 INT 56: F000:CA60 INT 57: F000:CA60 INT 58: F000:CA60 INT 59: F000:CA60 INT 5A: F000:CA60 INT 5B: F000:CA60 INT 5C: F000:CA60 INT 5D: F000:CA60 INT 5E: F000:CA60 INT 5F: F000:CA60 INT 60: 0000:0000 INT 61: 0000:0000 INT 62: 0000:0000 INT 63: 0000:0000 INT 64: 0000:0000 INT 65: 0000:0000 INT 66: F000:CA60 INT 67: C401:0004 INT 68: F000:CA60 INT 69: F000:CA60 INT 6A: F000:CA60 INT 6B: F000:CA60 INT 6C: F000:CA60 INT 6D: F000:CA60 INT 6E: F000:CA60 INT 6F: F000:CA60 INT 70: F000:CC20 INT 71: F000:CC40 INT 72: F000:CE80 INT 73: F000:CE80 INT 74: F000:D020 INT 75: 0000:0000 INT 76: F000:CCA0 INT 77: F000:CCC0 INT 78: 0000:0000 INT 79: 0000:0000 INT 7A: 0000:0000 INT 7B: 0000:0000 INT 7C: 0000:0000 INT 7D: 0000:0000 INT 7E: 0000:0000 INT 7F: 0000:0000 INT 80: 0000:0000 INT 81: 0000:0000 INT 82: 0000:0000 INT 83: 0000:0000 INT 84: 0000:0000 INT 85: 0000:0000 INT 86: 0A64:0020 ; TCLogo code; DOS: Used by BASIC interpreter INT 87: 1481:0020 ; TCLogo code; DOS: Used by BASIC interpreter INT 88: 131A:0020 ; TCLogo code; DOS: Used by BASIC interpreter INT 89: 0000:0000 INT 8A: 0A64:06BD ; TCLogo code; DOS: Used by BASIC interpreter INT 8B: 0000:0000 INT 8C: 0000:0000 INT 8D: 0000:0000 INT 8E: 0000:0000 INT 8F: 0000:0000 INT 90: 0000:0000 INT 91: 0000:0000 INT 92: 0000:0000 INT 93: 0000:0000 INT 94: 0000:0000 INT 95: F000:FEA5 ; TCLogo code; DOS: Used by BASIC interpreter; this is the original DOS int 8 interrupt vector INT 96: 0000:0000 INT 97: 0000:0000 INT 98: 0000:0000 INT 99: 0000:0000 INT 9A: 0000:0000 INT 9B: 0000:0000 INT 9C: 0000:0000 INT 9D: 0000:0000 INT 9E: 0000:0000 INT 9F: 0000:0000 INT A0: 0000:0000 INT A1: 0000:0000 INT A2: 0000:0000 INT A3: 0000:0000 INT A4: 0000:0000 INT A5: 0000:0000 INT A6: 0000:0000 INT A7: 0000:0000 INT A8: 0000:0000 INT A9: 0000:0000 INT AA: 0000:0000 INT AB: 0000:0000 INT AC: 0000:0000 INT AD: 0000:0000 INT AE: 0000:0000 INT AF: 0000:0000 INT B0: 0000:0000 INT B1: 0000:0000 INT B2: 0000:0000 INT B3: 0000:0000 INT B4: 0000:0000 INT B5: 0000:0000 INT B6: 0000:0000 INT B7: 0000:0000 INT B8: 0000:0000 INT B9: 0000:0000 INT BA: 0000:0000 INT BB: 0000:0000 INT BC: 0000:0000 INT BD: 0000:0000 INT BE: 0000:0000 INT BF: 0000:0000 INT C0: 0000:0000 INT C1: 0000:0000 INT C2: 0000:0000 INT C3: 0000:0000 INT C4: 0000:0000 INT C5: 0000:0000 INT C6: 0000:0000 INT C7: 0000:0000 INT C8: 0000:0000 INT C9: 0000:0000 INT CA: 0000:0000 INT CB: 0000:0000 INT CC: 0000:0000 INT CD: 0000:0000 INT CE: 0000:0000 INT CF: 0000:0000 INT D0: 0000:0000 INT D1: 0000:0000 INT D2: 0000:0000 INT D3: 0000:0000 INT D4: 0000:0000 INT D5: 0000:0000 INT D6: 0000:0000 INT D7: 0000:0000 INT D8: 0000:0000 INT D9: 0000:0000 INT DA: 0000:0000 INT DB: 0000:0000 INT DC: 0000:0000 INT DD: 0000:0000 INT DE: 0000:0000 INT DF: 0000:0000 INT E0: 0000:0000 INT E1: 0000:0000 INT E2: 0000:0000 INT E3: 0000:0000 INT E4: 0000:0000 INT E5: 0000:0000 INT E6: 0000:0000 INT E7: 0000:0000 INT E8: 0000:0000 INT E9: 0000:0000 INT EA: 0000:0000 INT EB: 0000:0000 INT EC: 0000:0000 INT ED: 0000:0000 INT EE: 0000:0000 INT EF: 0000:0000 INT F0: 0000:0000 INT F1: 0000:0000 INT F2: 0000:0000 INT F3: 0000:0000 INT F4: 0000:0000 INT F5: 0000:0000 INT F6: 0000:0000 INT F7: 0000:0000 INT F8: 0000:0000 INT F9: 0000:0000 INT FA: 0000:0000 INT FB: 0000:0000 INT FC: 0000:0000 INT FD: 0000:0000 INT FE: 0000:0000 INT FF: 0000:0000 What helped a lot in getting further into the TCLogo code per DOSBox-X debug log file was applying the “CPU = 8086” and “CPU speed of 8088 XT/4.77MHz” = 240 emulator cycles/ms options. That produces much smaller log files and got me faster to the timing sequence in TCLogo. I typed “TCLogo_s” in the program window (no return), then started the debugger, asked to log 200000 cycles, quickly returned to the program window and hit return. That took a while … the splash screen appeared, then the return prompt, then the logging was also done. I did not press return. The analysis of the log file took me quite some time – just to trace the output/input timing related things! This has nothing to do what TCLogo does as its main task: Providing a powerful programming language for (LEGO) robotics; this is just about the PWM timing loop. What happens upon TCLogo program startup in this regard is essentially the following. Note though that the segment:offset pairs shown below in the assembly code snippets are most probably different on other systems; these are from the debugger output of DOSBox-X, I have no clue if that changes on another machine. TCLogo is a true DOS COM file and thus should use only 64k of addressing, but I am not sure at all. Here we go: (1) Directly after startup at segment offset 100h, many things happen, memory is cleared, byte/words are “defined”, etc. I did not follow entirely through here. (2) At some point, the PWM signatures for the initial power setting of the 9750 outputs 0-5 (FF = 1111 1111 = power 7) are defined using four words. Each individual power PWM signature consists of 8 “serial bits”, as measured with the oscilloscope, shown in an earlier post in this thread. A further byte located at [9315] is set to 0, this is the mask for the 6 outputs; see below how the 6 bit parallel output signal to 9750 are (most probably) generated from the 8 bit signatures: 1481:0A0E mov word [9317],3F3F ;eight bytes are set to 3F = 0011 1111 1481:0A14 mov word [9319],3F3F 1481:0A1A mov word [931B],3F3F 1481:0A20 mov word [931D],3F3F (3) The presence of the interface is tested. This is where Alex has most probably hacked the original TCLogo software: First, 15h = 00010101 is sent out on the (hard coded) address (03F8) of the serial port, then TCLogo listens on this address for a reply of the same value. As my Arduino Nano does exactly that, just reply back what came in (plus the 2 input bits), TCLogo assumes a valid interface is present: 1481:0A26 mov dx,03F8 ;load serial port address into dx 1481:0A29 mov al,15 ;load 15h = bin 0001 0101 into al 1481:0A2B out dx,al ;write bin 0001 0101 to serial port 1481:0A2C in al,dx ;read serial port into al 1481:0A2D and al,3F ;al = al AND 3F (bin 0011 1111) 1481:0A2F cmp al,15 ;compare al to 15h = 0001 0101 1481:0A31 je 0A82 ($+4f) ;je=jump if zero flag is set; as the ;Arduino on the USB2Serial port replies ;with 0001 0101, the compare result is 1 ;= no jump TCLogo then stores this address two times; I believe these are the two other locations, Alex hacked TCLogo; one is used for the “out” command in the new interrupt 8 routine, providing the PWM signatures for the six 9750 outputs, the other for the “in” command reading the digital values of the two sensor inputs of 9750 in the same routine. Note that out/in addresses are identical for 9771 and the serial card, but different for the parallel card. Thus they are the same for TCLogo_s (serial version): 1481:0A87 mov word [9343],03F8 ;used for output 1481:0A8D mov word [9345],03F8 ;used for input (4) TCLogo stores a number of original interrupt vectors in an unused section of the DOS interrupt table, among these is int 8 = IRQ 0 (system timer interrupt), which becomes int 95 and points to the original BIOS section, where the system timing is handled. One example of how to get an interrupt vector is given below for int 5 = Print screen key: 1481:02B4 mov al,05 ;prepare call DOS int 21, function 35h (in ah): ;get vector for interrupt 5 (in al) - Print screen key 1481:02B6 mov ah,35 ;prepare call DOS int 21; return ES:BX = current int handler 1481:02B8 int 21 ;call DOS int 21 f35 i5 F000:D100 sti ;set interrupt flag; external, maskable interrupts enabled at ;the end of the next instruction F000:D101 callback 0038 (DOS Int 21) ;this loads requested data into ES:BX F000:D105 iret ;ES:BX now contains the (far) interrupt vector 5 (5) New interrupt vectors are copied into the interrupt table, among these is int 8 as well. DOS int 21, function 25h is used for this purpose, same way as above. The new vectors point to TCLogo code (interrupt service routines, ISRs). (6) The programmable interrupt timer (PIT; Intel 8253 on the XT, may be other but “compatible” timers on other DOS systems) is manipulated. I believe up-to the latest DOS version, int 8 = IRQ 0 is thrown every 55 ms, regardless of the hardware setup. On the XT, the CPU needs a number of peripheral chips to work the system, among them are the PIT and the Intel 8259 PIC (programmable interrupt controller). On the XT, the PIT uses a system crystal oscillating at 4.77 MHz. This frequency is divided by 3 = 1.193181 … MHz (for money saving reasons explained much better here: https://de.wikipedia.org/wiki/Programmable_Interval_Timer) and then further by a user accessible divisor register of the PIT. The original divisor is 65536; thus the system clock fires at 1193181 s-1 / 65536 = 18.2 s-1 => every 55 ms – as it apparently does on all DOS systems.To change the PIT clock rate i) the PIT mode may be (optionally) selected, then ii) the divisor latch has to be changed: (i) The PIT mode register is listening to I/O port 43h. TCLogo uses counter 0 of the PIT; low then high byte write to the 16 bit divisor register; runs the PIT in mode 3 (rate generator with symmetrical square wave output rather than short pulses); and sets the counter to 16 bit binary rather than BCD. The corresponding 8 bit word is thus 00-11-011-0 or 36h. (ii) The divisor latch of the PIT listens to I/O port 40h; TCLogo first writes A9h then 04h to this port = 4*256+169 = 1193 (decimal). (i) + (ii) assembly code: 1481:0358 mov al,36 ;00 11 011 0 = 36h 1481:035A out 43,al ;set PIT mode 1481:035C mov al,A9 ;divisor, low byte (A9h=169d) 1481:035E out 40,al ;write to PIT divisor latch 1481:0360 mov al,04 ;divisor, high byte 1481:0362 out 40,al ;write to PIT divisor latch 1481:0364 ret From this point on, the PIT fires with a frequency of 1193181 Hz/1193 = 1000.15 Hz => 0.9998 ms. This occurs before even the splash screen appears. (7) As TCLogo hooks int 8, the new interrupt service routine for int 8 (IRQ 0) needs to chain to the original int 8 BIOS routine (now int 95, which chains further to int 1C) every 55th time it was called; otherwise the system time and thus many things may screw up.The “count up” counter storage location is at [92FC] in the new int 8 ISR: (More code above; e.g. “PWM out” to and “sensor in” from the serial port connected to Arduino/9750) followed by 1481:0408 add word [92FC],04A9 ;this is the counter for calling int 95: ;04A9 = 1193 dec = 1/1000 of 8253 PIT frequency ;1,19318181818 … MHz) 1481:040E jnc 00000415 ($+5) ;(down) jump if no carry: Carry flag does not ;change here. It will change from 0 to 1, when ;[92FC] > FFFF. This will occur 55 times after ;this routine was called: ;55 * 1193 = 65615 = 1004F. ;4F is then stored in [92FC] - and thus adds up ;?to sync most accurately with system time? 1481:0415 mov al,20 ;20h=function "end of interrupt (EOI)" for PIC 1481:0417 out 20,al ;PIC listens on I/O port 20h 1481:0419 pop ds ;restore registers 1481:041A pop dx 1481:041B pop bx 1481:041C pop ax 1481:041D iret ;return from HW interrupt When the Carry flag is changing to 1 (this is during the 55th call of int 8) int 95 is chained (the original int 8 BIOS routine): (Same entry point as above) 1481:0408 add word [92FC],04A9 ;this sets the carry flag to 1: ;FBA6 + 04A9 = 1009E and thus int 95 is called; ;9E is stored in [92FC] 1481:040E jnc 0415 ($+5) ;(no jmp) no jump = int 95 call via seg:04AD 1481:0410 call 04AD ($+9a) 1481:04AD int 95 ;interrupt chain 1: int 95 ;(= original int 8 (IRQ 0) call) F000:FEA5 sti F000:FEA6 callback 0008 (IRQ 0 Clock) F000:FEAA push ds F000:FEAB push ax F000:FEAC push dx F000:FEAD int 1C F000:CC00 callback 0010 (Int 1c Timer) ;interrupt chain 2: int 1C F000:CC04 iret ;return from int 1C F000:FEAF cli F000:FEB0 mov al,20 ;only last chain ISR signals EOI to PIC F000:FEB2 out 20,al F000:FEB4 pop dx F000:FEB5 pop ax F000:FEB6 pop ds F000:FEB7 iret ;return from new int 95 That is pretty much it with regard to the I/O timing for the serial (and of course parallel or 9774 card) in TCLogo. PWM signal generation One last section on the PWM signal generation on the 6 out lines (0-5), which go to 9750 via either Arduino (TCLogo_s), the parallel port (TCLogo_p) or the 9774 card (TCLogo). Upon further inspection of the int 8 routine (again using the DOSBox-X debugger log repeatedly, but logging after hitting return and setting each output to an individual power level (6x “tto X”; “setpower Y”; “on”), I believe to having understood, how that works. The PWM signatures are 8 bit serial “packets” continuously sent out at a 1 ms rep rate to the 6 individual output lines. These packets are re-calculated only, when the user changes the power setting. They are stored as bytes in locations (cf. section 2) [9317] to [931E] Let us assume the following: TCLogo Settings: talkto setpower on/off ---------------------- 0 1 on 1 2 on 2 3 on 3 4 on 4 5 on 5 7 on The output mask byte at [9315] is now 00111111 = 3F=all on Tracing "out dx,al" in the consecutive int 8 code calls (every ms) yields: (9750 output#: 54 3210) 1) 1481:0394 out dx,al ;AL: 3C = 0011 1100; byte [9317] 2) 1481:0394 out dx,al ;AL: 32 = 0011 0010; byte [9318] 3) 1481:0394 out dx,al ;AL: 3C = 0011 1100; byte [9319] 4) 1481:0394 out dx,al ;AL: 29 = 0010 1001; byte [931A] 5) 1481:0394 out dx,al ;AL: 36 = 0011 0110; byte [931B] 6) 1481:0394 out dx,al ;AL: 38 = 0011 1000; byte [931C] 7) 1481:0394 out dx,al ;AL: 3C = 0011 1100; byte [931D] 8) 1481:0394 out dx,al ;AL: 23 = 0010 0011; byte [931E] (9750 power level: 75 4321 -> as measured) The columns “9750 output#” 5->0 represent the PWM signatures for each 9750 output. These signatures are thus as listed below, in full accord with the oscilloscope data: 7: 1111 1111 = FFh = 255d (6: 1111 1110 = FEh = 254d) ;not used in the above experiment) 5: 1110 1110 = EEh = 238d 4: 1011 0110 = B6h = 182d 3: 1010 1010 = AAh = 170d 2: 0100 1001 = 49h = 73d 1: 0001 0001 = 11h = 17d (0: 0000 0000 = 00h = 0d) ;not used in the above experiment In conclusion (on PWM output generation): TCLogo calculates and stores 8x8-bit data (bytes) each time the power data of 1 (or several) channels is (are) changed. The new PWM data have to be calculated only once after the change(s) and then simply 1ms repetitive mov/out instructions generate the PWM pattern for all 6 outputs, which saves a lot of time within the interrupt routine. This behavior is readily replicated in QuickBasic – but it takes much longer to execute – certainly not at 1 ms rep rate! But it works as expected. Nevertheless, the TCLogo code is simply beautiful!!! Summary I believe it may be worthwhile to program this behavior into the QuickBasic program I am currently using for controlling 9750 also with PWM. So far the outputs are simply “on” at power level 7 or off. Nothing in between. The nice thing is that QuickBasic does not claim any of the new interrupt vectors, TCLogo is occupying for hooking. So I can maybe do some c/p’ing here. Who knows, it will be a (very) long journey for sure! All the best, Thorsten (P.S.: Will edit this surely quite often, as there will be many typos) Edited May 20, 2023 by Toastie Quote
alexGS Posted May 20, 2023 Posted May 20, 2023 (edited) Hello Thorsten - nice work with proving the operation of the 1ms interrupt timer for the PWM - that explains how it works consistently across systems of different speeds. I think you will be successful in your quest to use the same approach from QuickBASIC (or QBASIC?) Thank you for your kind words about my ‘hacking’ - and for proving that the use of the port address in three places is (i) for testing the port, (ii) for outputs, and (iii) for inputs - I appreciate that. Meanwhile, I have had some difficulties with parallel port use on later laptops from the early 2000s, but since these usually have USB ports as well, I hope to try using USB to feed the (relatively hungry) 5V supply to the Interface A of the later type with the flat-top LEDs. I need to do a little more testing to check this solves the problem of not being able to activate more than two or three outputs simultaneously. The parallel port alone cannot supply enough current in this situation (it can for the earlier interfaces, or for earlier laptops). Last night I became aware of this rather-bizarre piece of new hardware:https://www.aliexpress.us/item/1005005528944178.html It has sold out already, even at the rather high price for what it is. You’ll notice that while it doesn’t have a printer port, it does expose the ISA bus - so could support a version of the LEGO 9771 card - check your post above for the typo under “PWM Signal Generation” ;) All the best -Alex Edited May 20, 2023 by alexGS Quote
Toastie Posted May 20, 2023 Author Posted May 20, 2023 (edited) On 5/20/2023 at 4:24 AM, alexGS said: Last night I became aware of this rather-bizarre piece of new hardware: Hi Alex, WHAT A FIND!!! Oh my - hopefully this comes back alive - will purchase one right away!!! How cool is that. I love the way they expose the CPU and other chips ... beautiful, simply beautiful!!! I shall also plow Tindie.com for similar things ... Will come back later ... back :D Yes, I also believe the USB or any other power supply providing 5V/100(+) mA should do the trick. In the schematics for 9750, LTV-817 M is listed as (4x) opto-coupler. Each draws 10 mA (max.) when on, if I am not mistaken (5V/560 Ohm). All couplers on = 60 mA max. The ULN2003 easily sinks that current. All the best, Thorsten Edited May 21, 2023 by Toastie Came back :D Quote
Toastie Posted May 22, 2023 Author Posted May 22, 2023 (edited) Hi all, just to wrap up the hardware setup(s), I am currently using for the operation of interface A / #9750 with the computers I have, particularly the IBM XT / #9771 interface card <=> #9750 combo and my win11 laptop USB <=> Arduino <=> #9750 combo. This is for direct operation of TCLogo.com (original, TCLogo_s, TCLogo_p) and/or QuickBasic 4.5 or QBasic 1.1. Essentially all computers (vintage/ISA, direct cable, serial-Arduino, USB-Arduino should work with one of the options shown in the picture below: Figure legend (A) IBM XT or any compatible system with ISA bus (or directly addressable bus system via out/in CPU commands) available. The communication is via ISA cards; either LEGOs #9771, parallel, and/or RS232 serial card. (B) Semi-vintage computer, i.e., one with parallel or serial port available, again directly addressable, as in (A). (C) Modern computer lacking any directly addressable serial/parallel ports - this requires a DOS emulator, here DOSBox-X. 20 ribbon cable = 20 wire flat cable which attaches directly to 9750. S2T = Serial (RS232) to TTL adapter; this is for BASIC programs using the serial port or TCLogo_s to operate 9750 via an Arduino "serial-to-parallel adapter" U2S = USB to serial (RS232 adapter); this can be used on modern machines for RS232 serial communication. As my Arduino is a one-4-all solution, this is the most flexible approach as it works flawlessly with all computer systems I tested. U2T = USB to TTL adapter; this is for computers with USB port only, as in the U2S <=> S2T approach. The charm is that the U2T +5V line can be used to feed power to the Arduino as well, just connect +5V out of the adapter to the +5V power rail of the Arduino board, it can't do any harm. DB-X = DOSBox-X emulator with serial port emulation enabled. The "/" broken line means long cable can be used. Arduino = Arduino Nano, Uno, Mega - these are the ones I tested - they all work fine. For the Nano, this program works fine as serial to parallel converter (note that the direct port addressing is specific to the specific Arduino boards): https://bricksafe.com/files/Toastie/lego-interface-a---9750---9771---tclogo/program-files-/9750_Parallel2Serial_Interface.ino Note 1 on the Arduino: The Arduino needs +5V as power supply; this is not shown here. The Arduino supplies/sinks 20 mA (cont) on each output pin (200 mA total); this should be more than enough for all 9750 varieties out there. Note 2 on the Arduino: The Arduino USB port for programming/power supply does not show up as "com port" in device manager and can thus not be used as com port device for serial / in/out communication in DOSBox-X. You need to use a USB to serial or USB to TTL adapter as com port, which can then be configured in DOSBox-X. Note 3 on the Arduino: The Uno and Nano have only one hardware serial port, RX/TX. These two pins are exposed on the board, but do also connect to the on-board USB chip for programming/power supply. I am not trusting the software serial solutions very much. When attaching the U2T or S2T adapters to the RX/TX pins directly, programming of the Arduino via USB port does not work anymore. There is a very simple solution: Either remove the adapter cable that goes to the RX pin when programming or put a simple switch in between that line. The TX pin on both the adapter and on board USB chip does not interfere at all. See also photograph on page one of this thread. Note on custom parallel cable: As noted by @alexGS, not all parallel computer ports can drive the 9750 opto-coupler input circuity; in this case, an additional +5V power supply is required here as well. Note on operating system: Essentially all DOS versions should work running TCLogo and/or BASIC; I tested DOS 3.3 (MS and PC/IBM versions). Win98 DOS prompt works as well. Not sure about WinXP. All other Windows consoles do not; for Win11, the DOS emulator DOSBox-X is working fine. Guess this is it. All the best, Thorsten Edited May 22, 2023 by Toastie Quote
RyBreaddddd Posted July 2, 2023 Posted July 2, 2023 Hello Thorsten, Alex, and others, Thank you for one of the most interesting threads I've ever read! I like to consider myself relatively computer-adept, but I'm definitely a little out of my element here ... I like fiddling with older LEGO electronics; recently I've been playing with the 90s Control Lab and VLL with the scout, and I finally decided to conquer the Interface A. I have the Interface itself, a USB to TTL adapter, Arduino Nano, and a hodge podge of ribbon cables. I understand (based on your most recent post on this thread, @Toastie) that's all I need to get the interface running on my modern computer via DOSBox, correct? I'm only unsure about which arduino pins to connect to which pins on the interface. If you could help me figure that out, I would be greatly appreciative! Thanks for all your work on this, -Ry Quote
HydroWorld Outlook Posted July 2, 2023 Posted July 2, 2023 Yes, thank you so much for this thread. I found these tips and tutorials very helpful indeed. Quote
Toastie Posted July 2, 2023 Author Posted July 2, 2023 3 hours ago, RyBreaddddd said: If you could help me figure that out, I would be greatly appreciative! Hi Ry, nice that more folks are enjoying vintage LEGO! Now when you navigate here: you can see in one of the pictures how the Nano is connected to the Interface A: Arduino pin Lego Interface A pin D2 6 (to LI output 0) D3 8 (to LI output 1) D4 10 (to LI output 2) D5 12 (to LI output 3) D6 14 (to LI output 4) D7 16 (to LI output 5) D8 18 (from LI input 0) D9 20 (from LI input 1) Lego Interface A pins 5 - 19 are GND and 1+3 are +5V. The USB to TTL adapter outputs go to TX and RX on the Nano - make sure you have an on/off switch in the RX line, otherwise you can't program the Nano on the fly. This configuration works only with a Nano running my little program available on Bricksafe, as I am using direct register manipulation (for fun ...) And lastly: I have tested this with DOSBox-X only. No idea whether DOSBox works as well. All the best, Thorsten Quote
alexGS Posted July 4, 2023 Posted July 4, 2023 (edited) On 7/3/2023 at 6:39 AM, RyBreaddddd said: I finally decided to conquer the Interface A. I have the Interface itself, a USB to TTL adapter, Arduino Nano, and a hodge podge of ribbon cables. I understand (based on your most recent post on this thread, @Toastie) that's all I need to get the interface running on my modern computer via DOSBox, correct? I'm only unsure about which arduino pins to connect to which pins on the interface. If you could help me figure that out, I would be greatly appreciative! Thanks for all your work on this, -Ry Hello Ry - sorry I’m late to the party (again) - not enough free time here at the moment, sometimes I have a lot and other times little (self-employed)… Thorsten has made a nice diagram above showing that there are different approaches, and he has done an enormous amount of work to test and refine the Arduino-based serial-to-parallel conversion for a modern PC. Meanwhile, I’d like to point out that the parallel cable approach (B) is still a simple way to go - IF you happen to have suitable old PCs lying around that have parallel ports and boot into DOS or Windows 3.1/95/98. My requirement is that it must allow the use of the TC-LOGO programming environment as described in the original materials (e.g. the Reference Guide downloadable from EvanK’s page at the Internet archive; search ‘vintage LEGO robotics). That’s why the hack came about; to allow TC-LOGO to run without the original ISA card. And the PWM (Setpower) still works, since that’s done in software as Thorsten proved. I happen to have a 1995 Compaq Contura 410/1994 Contura Aero (Win 3.1), 1999 Toshiba Satellite 4800 (Win 98), and 2004 Compaq Evo n620c (Win 98) - actually a couple of each - and these are all laptops with native parallel ports that work with the interface cable. The 9750 interface with the flat-top LEDs may require a ‘boost’ from a USB port to supply the 5V to the interface, which is easy on the latter two machines as they include USB ports. The older 9750 interface with round-top LEDs doesn’t require the ‘boost’. EDIT: I just tested with the Contura 410C and the flat-top LED interface works fine without the extra ‘boost’. So that’s still the way I do it, just a parallel cable without Arduino and without DOSBox (although I feel guilty for not using Thorsten’s solution!) I think it’s up to you to decide which path you’d like to take. I like collecting and restoring early laptops - 1994-era is old enough for Interface A in my opinion, even though it also works with Control Lab (Interface B). To quote a LEGO ideas book from the 1980s - “the most important thing is to use the bricks you have in new ways. Have fun!” -Alex Edited July 5, 2023 by alexGS Quote
Toastie Posted July 5, 2023 Author Posted July 5, 2023 (edited) On 7/4/2023 at 11:29 AM, alexGS said: My requirement is that it must allow the use of the TC-LOGO programming environment as described in the original materials Hello Alex! You are absolutely right - and it should be stressed: Nothing is better than using a direct hardware approach, particularly when the hardware is still readily available (semi modern PCs and laptops, eBay is your friend) and b) "all" you have to do is making a cable AND carefully follow the instructions provided by you for making such a cable!!! I screwed up on this initially, because I was NOT carefully reading the instructions. The good old world of schematics and focused work on multiple wires ... I love that. I'd also say that the parallel approach/access to 9750, either via 9771, the Apple equivalent, or any true PC parallel port, is much "closer" to the original setup. The Arduino/serial approach just works because hardware has become so much faster over the years. Back in the TC days, it was simply not possible to do PWM via serial communication, as discussed above I have been seriously side-tracked by @evank as Evan told me, there was no version of TC available for Atari's. I resurrected a working Atari 1040 STFM and a Mega St4 from being trashed (BTW: NO more vintage stuff anywhere in the basement of my institute - nothing. Today it was cleared entirely. Sneaked in on Monday and snatched the Atari's - today, everything else was relocated to Building A = trash & recycling. Interestingly, this building is right next to Building B (duh) = Administration: Rectorate etc. pp. :D). As BASIC is BASIC, I am entertaining the idea of adapting my DOS QBasic program to GWGFABasic ... the Atari's provide direct access to the data/address bus . We'll see. No time right now, but 5 and 1/2 years and I'll retire All the best, Thorsten Edited August 4, 2023 by Toastie Quote
alexGS Posted July 6, 2023 Posted July 6, 2023 Nice one, Thorsten - again, I really respect that you have developed the idea of the old software on modern hardware with a new USB interface as a workable solution :) And then; yes, writing one’s own software opens up all kinds of platforms and possibilities! An Amiga from the period has a parallel port, perhaps it’s possible to control with AmigaBASIC, I mean to try that. And someone gave me a Psion Organiser - a handheld thing that appears to include BBC BASIC and a number of I/O lines. I joined the dots and wondered if it’s possible to control Interface A with it; the two-line LCD is rudimentary, may not be worth the trouble ;) but it would be a ‘period’ hack… Then finally there’s the idea of using a RaspberryPi, with programming in Python or Scratch (a modern hack). Although at that point it’s perhaps easier to forgo the Interface A altogether and use modern motor controllers and IR sensors (something I’ve done already). -Alex Quote
Toastie Posted August 1, 2023 Author Posted August 1, 2023 (edited) Hi Alex, (I am trying to have the Dacta Control lab thread of Brian untangled, let's see what happens) with regard to the additional 5V supply required for some of the parallel port/9750 combos using the method you describe above: For my PoweredUp/TC "coupling", I used the permanent ~4V DC output from 9750 to supply 9V DC to the Technic hub with the help of miniature step-up-converter (https://www.eurobricks.com/forum/index.php?/forums/topic/194832-lego-technic-control-tc-1986-meets-lego-poweredup-pup-2019-bridging-a-30-years-lego-technic-electronics-“gap”). Now, I believe you can either use the 4V DC directly to power the opto-couplers of 9750 directly, i.e., feeding that power into 1+3 (+) and any of the even pins (GND). This way, you won't need an external power supply. This "violates" TLGs approach of not exposing any 9750 voltage to the controlling computer or interface card, but whatever. Should that voltage not be high enough, the little step-up-converter would easily do it, as it produces the 9V DC for the hub without any problems. Not that it makes any difference, it would just look cool ;) Best, Thorsten Edited August 1, 2023 by Toastie Quote
alexGS Posted August 1, 2023 Posted August 1, 2023 (edited) Thanks for the idea, Thorsten :) Worth a try, using the 4V to supply the Interface A’s optocouplers instead of relying on parallel port control outputs. The laptop PCs that were having problems turning on the outputs were new enough to have USB ports, so I decided taking the 5V from USB was the easier ‘fix’; I think it’s electrically better to have the 5V coming from the PC rather than externally, but I could be wrong. There doesn’t seem much ‘rhyme or reason’, i.e. no obvious pattern to which laptops can turn on enough outputs or which laptops need this 5V boost. I was disappointed that my 2004 Compaq Evo laptop had difficulty where my 2002 Toshiba did not. I think on balance, Toshiba seems a good choice of retro laptop :) Thank you for your efforts to move the Interface A software discussion into a new thread. It was confusing me when I had email notifications about the Control Lab thread updates. Incidentally, for the sake of completeness in this thread, here is my document about the parallel port cable (trying to make it easy for anyone who stumbles into this). https://bricksafe.com/files/alexGSofNZ/interface-a-tc-logo/ParallelPortInterfaceAConnection.pdf Edited August 1, 2023 by alexGS Quote
Toastie Posted August 1, 2023 Author Posted August 1, 2023 1 hour ago, alexGS said: I think it’s electrically better to have the 5V coming from the PC rather than externally, but I could be wrong. No, you are not, as far as I am concerned; this USB supply approach >is< he much better and more "in line with TLGs" philosophy way to do it. 1 hour ago, alexGS said: here is my document about the parallel port cable This is just a marvel! Thank you so very much for composing this document. It is of true teaching style - meaning it is a tutorial, a reference, and an instruction. The best of three worlds! All the best, Thorsten Quote
BatteryPoweredBricks Posted August 24, 2023 Posted August 24, 2023 Just found this video today, I'm sure most of the information is known to folks in this thread but I'm glad it exists! If nothing else it's something to share with people who haven't seen it before without having to explain everything from the ground up Quote
Toastie Posted August 24, 2023 Author Posted August 24, 2023 Hi Brian, what a nice find!!! And Aaron must be soooo excited and totally in LEGO heaven ... Thank you very much for sharing! All the best, Thorsten Quote
alexGS Posted August 24, 2023 Posted August 24, 2023 (edited) 1 hour ago, BatteryPoweredBricks said: Just found this video today, I'm sure most of the information is known to folks in this thread but I'm glad it exists! If nothing else it's something to share with people who haven't seen it before without having to explain everything from the ground up Thanks for the video link! I hadn’t seen it - the video is produced to a very high standard, well-edited, nice and concise, very clear (accent is pleasant to those of us overseas), no egregious errors in the technicalities that we know so well. This would be an ideal sales video for @evank ; he has some of these hardware/software packages available 😁 Edited August 24, 2023 by alexGS Quote
evank Posted August 26, 2023 Posted August 26, 2023 On 8/24/2023 at 5:33 PM, alexGS said: no egregious errors in the technicalities Except that the video title says 90s! It should be 80s. Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.