Showing posts with label serial. Show all posts
Showing posts with label serial. Show all posts

Thursday, 8 August 2019

Linux->Falcon serial transfer

After having a look at the Atari Falcon 030 and using the cumbersome floppies for moving files about, I wanted to move files over the serial.

I had lost my null-modem cable and could only find a mirrored 9-pin cable with M-F connectors (what is that for anyway?). The proper null modem cables were still sold at Clas Ohlson in Helsinki. Thanks, Clas Ohlson!

Serial is quite fast for sending a few megabytes or less, which is enough as Falcon files are not that huge.

Obviously, the ports have to be set for the same speed. 115200 proved to be a bit too much, so I went for 57600, which gave a healthy ~5500 bytes per second.

First, I need to set the serial port parameters using the Control Panel. This requires the Control Panel accessory (XCONTROL.ACC) in the boot drive folder and the serial control panel extension (SERIAL.CPX) on the system, at C:\CPX\ for example.

DRVIN.PRG needs to be at the AUTO folder to gain these high speed connections for "Modem 2", otherwise you'll be stuck with the 9600. Edit: It seems the SCC.PRG should be there too. Not sure which of them or both?

If DRVIN is not there, the ACC is likely to bomb if you try to fiddle with the modem 2 parameters.

XYZ on a command line shell at Atari end

To receive files using the ZMODEM protocol, you need XYZ.TTP.

Although the xyz can be run from the desktop, I prefer to use these TTP (TOS-Takes-Parameters) programs from inside a command line shell. It's a bit neater that way and I get to see the program results and recent actions better. Moving files around the system becomes quicker too.

Still testing at 9600, hence the slow speed...
Okami shell is reasonably featured, and you can use some Unix-style parameters, like directing output to a file or a serial port. It's not developed with a Falcon in mind, but using a 2-color video mode it's pretty fast. "mupfel" is another shell, but setting it up seems a bit more involved so I'll look at it later.

I added the following line inside the Okami "profile" file, so the shell will execute it on running. This way I can run the xyz from wherever I happen to be:

xyz=c:/xyz202b/xyz.ttp

Afterwards, using

$xyz

the xyz.ttp will run and wait for a file to be sent. Yes that $ is not exactly as effective as an alias or a proper PATH but it's still far better than working every time from within that folder.

As an aside, editing that profile file is bit of a chore as there are very few choices of a shell-run text editor. I'd hate to jump between a GEM editor and the command line shell now that it's in place. I ended up using something called pro_edit for now, which is rather poor and assumes the display height is 400. ST video modes to the rescue.

But if it's only a matter of adding one line to the profile, then appending that line with echo xyz=c:/xyz202b/xyz.ttp>>profile will work.

Obviously, after the file transfer is in place text files could be transferred from the Linux... But as the point is to toy around with the Falcon, why move over all the tasks to some other computer?


sz at Linux

Unlike Atari, Linux doesn't have an abundance of strange 'terminal emulator' programs, possibly because the terminal is so integral to the system.

There's minicom, but practically minicom (or anything else) uses rz and sz for file transfer protocols, so it's better to use these from the Linux terminal command line directly.

These need to be installed first. If there is a permission problem with the serial port then the user has to be added to the dialout group.

I followed a suggestion of calling sz from a tiny script (named zsend in the example) which ensures the serial port speed is correct:

#!/bin/sh

DEV=/dev/ttyS0

stty -F $DEV 57600
sz $1 > $DEV < $DEV

The ttyS0 is the device for the serial port, in my case it's already a part of the motherboard. An USB->RS232 port is often called ttyUSB0. dmesg | grep tty reveals the device names.

Saving this script as zsend, it can be made into an executable with chmod +x zsend, after which ./zsend filename should start the transfer. If Atari is running the xyz.ttp and waiting, then the file should transfer.

A version for receiving files from the PC end, use rz instead of sz.

At TOS, xyz -u filename will upload a file, defaulting to ZMODEM.

I also tried batch uploading with *.* and although everything went fine for a file, the XYZ.TTP at Atari end complained about too many handles or something after about 16-17 files. So, for moving a lot of files it's better to zip things at that end first, no matter how slow it is.

Strangely, uploading from Atari was a bit slower, some times less than 4000 bps on average. File permissions may need altering on the Linux end and the filenames tend to be uppercase which can be a bit annoying at Linux. -LL option on zip ought to force filenames to lowercase, though.

Backing up AUTO folder and your essential system files with this method is a good idea I think!



At Atari again

Transferring zip files is much more handy than trying to send files with a folder structure, and they are obviously compacted too.

Working with the Okami shell, for added comfort I also added the zip unpacker to the Okami profile:

zip=c:/packers/stzip/zipjr.ttp

...for example. The zipjr.ttp comes out of the stzip.tos self-extracting archive, found here.

$zip -xr file.zip

In Okami, this then becomes the equivalent of running zip from its folder. It appears the zip version I have it likes explicit -xr parameters for extracting and preserving the folder structure.

Lharc (lzh) is another often seen archive format, and jaymsa18 may be used for recovering files out of .msa and .st disk images on the Atari end, if the disks play nice with file structure that is.

After all this, I can finally look at Llamazap, an apparently unfinished game by Jeff Minter that can't even be started without a very specific controller. Oh, well.


Thursday, 17 January 2019

IRQhack64 serial transfer


Previously I had only used my IRQHack64 to load files from the SD card. I now wanted to turn to the transfer functions, enabled by the 6 pins sticking out of the cartridge.

The transfer is something that potentially brings the cart to a whole new level. With this port it's possible to send a file over the serial and the C64 runs it automatically.

Just to make this clear, IRQHack64 is not a substitute for a C64 serial port, it doesn't connect a modem, internet or MIDI. Your PC communicates with the Arduino inside the cart, and the Arduino+EPROM work their magic with the C64.

But as the Arduino inside the cart is not limited by C64 hardware speeds, the files move at a nice 57600 rate, and they move over to C64 even faster.

I have postponed testing his because firstly I knew it would probably be a chore, as the IRQHack64 software is not very clearly documented. All the sources have been made available, but there's no overall comprehensive guide for what the cart is supposed to do and how.

Also, the Arduino code, the EPROM code and the irqhack64.prg need to have compatible versions or the cartridge likely won't work.
Connecting the PC to the cart using an FTDI board
More importantly, I needed the FTDI board, which makes it possible to communicate with the Arduino Pro Mini inside through serial, while the cart is on-line.


Converting the IRQHackSend

I used the IRQHack64Turbo project as a starting point for examining what the software is supposed to do. At least after compiling the Arduino source I get a working cartridge that plays nice with the current EPROM and the menu program.

The IRQHackSend in the Tools folder is a separate software for sending files from the PC end. It was simple enough to adapt to Processing.

The program opens a 57600 connection to the Arduino inside the IRQHack64, sends the "1" character which tells the Arduino at that end to start receiving. After this the Processing source sends the file length bytes, two header bytes and data bytes just as the original source does, with suitable delays here and there.

Immediately I got my software to talk with the cart, as the IRQHack transmits the menu and other responses over the serial. Using single character commands over the connection, the C64 can be reset with or without the cartridge, the cart menu software can be triggered remotely from the serial and so on. This remote control-reset was a nice bonus. So far so good.

However, using the file transfer mode was not a success, as the resulting bytes were often garbage. For a while I thought the serial transfer was to blame, and I spent hours messing around with the Arduino source.


The Obvious Solution

Umm, it turns out there is a speed toggle that apparently affects how the memory write works. The cart might have even have worked out of the box (not that it came with a box), but I could have changed that accidentally. The serial was not to blame at all, at least with these small file sizes.

The source seems to indicate it's possible to change the speed through the time-based button press interface using more than 5 seconds pressing. The source is also where I found this feature even exists.

I changed the Arduino source so I could send the speed toggle through a serial command, so I could be more sure that it has been received. After that, the serial-transferred files & memory writes started working!

Below is a Processing source for sending a file over to the IRQHack cartridge, using the FTDI board as a serial port.


import processing.serial.*;

Serial myPort;

void setup()
{
  int port = -1;
  for(int i=0;i<Serial.list().length;i++){
    String stn = Serial.list()[i];
    println (i+":"+stn);
    if(stn.indexOf("USB0")>=0)port=i; 
  }
  if(port>=0){
    String portName = Serial.list()[port];
    println (portName);
    myPort = new Serial(this, portName, 57600);}
  else{
    println("NO USB found");
  }
}

void waiter(int amount){
  for(int i = 0;i<amount/10;i++){
    if (myPort.available() > 0)print (char(myPort.read()));      
    delay(10);
  }
}

void keyPressed(){
   int k=key;
   if(k=='1')send_file("myfile.prg"); // send this file
   if(k=='r')myPort.write('3'); // reset c64
   if(k=='c')myPort.write('4'); // reset c64 nocart
   if(k=='d')myPort.write('2'); // enter dir menu remotely
}

void send_file(String fname)

  myPort.write('1'); // "type" the Receive prog command at Irqhack's menu via serial

  byte prgdata[] = loadBytes(fname);
  
  waiter(250); // 250*10 millis, original delay(2500) millis
  
  byte low = (byte)(prgdata.length % 256);
  byte high = (byte)(prgdata.length / 256);
  
  myPort.write((low)); // write length to receiving end  
  myPort.write((high));
  
  for(int i=0;i<2;i++){ // write prg header
    myPort.write(char(prgdata[i]));
    if((i%32) == 0)delay(10);
  }
  for(int i=2;i<prgdata.length;i++){ // write actual data
    myPort.write(char(prgdata[i]));
    if((i%32) == 0)delay(10);
  }
  // we're done here
  waiter(1000);
}

void draw()
{  
  if (myPort.available() > 0) print (char(myPort.read()));         
}

This is a minimal Processing sketch. I've only tried it on Linux. It scans the serial list for the presence of the string USB0, this may vary depending on your computer and serial adapter/FTDI hardware.

The program reads all incoming characters and prints them on the console. Pressing '1' will send a file myfile.prg over the serial, if it exists. R and C keys resets the C64 and D makes the IRQhack enter the file selector menu. If there's no Arduino source change, there's no point sending a 'speed toggle' command.

Now that I already made the work on Processing, I modded the PETSCII editor to save & upload the exported prg through a keypress, so I can do PETSCII graphics on PC screen and experiment with results on the C64 screen.

After reducing the pre-delay in my sending routine to 250ms, it takes about a second to transmit the 2K PETSCII prg, so I can do it as often as I like. This was initially at 2000ms. It may be that different C64 units need a slightly different delay.

I've worked on it a bit more for my own setup.
Using the same approach on my Multipaint, it obviously works but as the export file sizes are 10K it already takes closer to 4 seconds to see the results on the C64 screen. But that's not bad at all. I could also revise the Multipaint export so it would send a smaller file in case less than full screen area has is in use. Sending packed files isn't that useful as the C64 will take some time extracting them.

This is still a great improvement over the SD card switch-a-roo between PC and C64. This feels like a real professional Commodore 64 graphics workstation!


Not so fast

I came across problems when transferring some small scene demo and game programs that would normally run from the SD card. Although size is not the only cause, it seems larger files (20K+) are more likely to fail.

I have to stress there is no randomness here, trying to send the same file repeatedly does not help, nor do the small straightforward files really ever fail to send.

*

To extend my review of IRQHack64, I'd now say the serial transfer/remote features are a very nice addition to a developer's toolbox, but it doesn't add much value to a casual user or game player.

For the above purposes, sending simple & short files repeatedly, the cartridge transfer functions still performs fine. For longer files and demo/game collecting it is better to move them on the SD card anyway, from where they can be run more reliably.

The cart receives a file and run it, although it would be in some situations more useful to send memory areas to C64 without resetting or running any code, for example overwriting portions of the graphics memory. But, without changing the EPROM code this situation probably can't be changed.

Sunday, 26 January 2014

Sinclair QL Serial


The Sinclair QL serial port can be used for poor man's file transfer between a PC and QL, but as usual the knowledge needed for doing this is not in handy one place. Continuing to celebrate the QL's thirtieth anniversary with some beginner-level material, I'll have a look at practical serial communication between the QL and PC/Mac.

The cable on the QL is end is similar to these puppies, a 6-pin BT.
The pictured plug had to be carved slightly to fit the QL.

First, the cable. The cable is connected to the SER2 on the QL. There are also QL's with 9-pin ports, and the image below depicts the original UK connector. Apparently the 9-pin connectors have a different pin order than a PC RS-232.

A 6-pin BT plug might be difficult to get so the more adventurous hackers might be better off by modifying the connector itself. The plugs appear to be similar to a British telephone standard. Googling for a "British Telecom Plug" ought to reveal sites for buying a cord. It's not a 100% fit, but as long as they have the correct number of pins, the plastic shape may be modified.

A 630W appears to be the exact right model, but I've yet to see anyone sell them new. There are also left-hand and right-hand versions, for example I have a CTL-fitting 9-pin converter which cannot be made to fit the SER port.

I can't imagine how many times I've soldered a cable as a mirror image. The confusing thing is, that here a mirrored cable "sort-of" appears to work, because the transmit pin is in the middle of the 9-pin connector.

This should be correct and the one I use currently. Both connectors are depicted as they are seen from outside the computer.

Connection between the QL and the PC 9-pin serial connectors, as viewed from the outside.
Obviously not to scale! SER2 1:GND,  2:TxD, 3:RxD, 4:DTR, 5:CTS

The next step is to make the computers talk to each other. A terminal program at the PC/Mac end, such as Zterm, may be sufficient for testing the connection. Oh, and your PC/Mac might be one of those new-fangled computers without a 9-pin serial port. So you'll need to have an USB-RS232 adapter.

After all the hassle, on the QL end, you can use a program like this for scanning incoming text:

10 BAUD 2400
20 OPEN #8,ser2
30 I$=INKEY$(#8)
40 PRINT I$;
50 GOTO 20

Edit: Of course it's 50 GOTO 30, as pointed out in the comments :)

With a terminal set to 2400 on the PC/Mac end, you can start talking between the computers. Of course it's not very reliable, but some of text typed in the terminal ought to show on the QL screen. You can test the reception of the PC end by writing PRINT #8,"Hello!" on the QL.

File transfer


After testing the connection it's time to move to more interesting topics.

QL BASIC files can be transferred to PC via serial:

SAVE ser2

With a terminal using the same speed setting, you can grab the basic listing from the terminal window, and maybe copy/paste it to a text editor for storage. To send files to QL, your terminal needs to have functionality for sending files in plain ASCII, terminated with character code 26.

LOAD ser2z 

The QL will wait for a BASIC listing to be sent. (The 'z' is there to indicate that the terminating character will be expected.)

But how to send binaries and raw data?

LBYTES ser2,131072

...makes the QL expect raw data, which will be placed from address 131072 onwards (the screen memory). But before the actual data, there has to be a header, otherwise the QL can't know how long the file will be. (The code 26 cannot be used as a terminator, as the data itself might contain the value.)

From the PC end, headers can be examined by viewing the incoming serial data in numeric format. (Not usually possible in a standard terminal.) Data can be sent to the PC by using SBYTES ser2,131072,16 (for example). There are apparently more complicated headers, but this is the simplest way and the QL does not seem to use anything else for the SBYTES.

Header:

[255]
[length highest byte]
[length]
[length]
[length lowest byte]
[0]
[0]
[0]
[0]
[0]
[0]
[0]
[0]
[0]
[0]
[byte x length of actual data...]

So, sending a file with a length of 16 bytes would mean sending this data over the serial:

255,0,0,0,16,0,0,0,0,0,0,0,0,0,0,11,22,43,54,25,64,17,108,19,20,44,22,13,11,10,6

(The 16 bytes here are just bogus numbers)

QL loader


Below is a small Processing source for sending files to the QL. As a simple terminal is handy enough for receiving BASIC files, I did not bother with reception functionality. Copy and paste the source into your Processing editor and run it from there.

It might be used for building some kind of file repository for QL. The program assumes you have the required file stored in the Processing folder for the program. (In this case, QLDATA.BIN and/or QLBASIC.BAS)

Use the b key to send BASIC files and s for sending binary data. The BASIC file should be a plain text ASCII file.

It ought to be obvious from the source how to add or change your own filenames. With binary, I'd recommend loading to screen memory for testing. This way you'll get an immediate visual response as the screen fills with data. Executable code has to be run with CALL command.

Sadly, 2400 baud seems to be the fastest reliable speed for loading directly. At least I could load 32k and 48 k files without any apparent errors.

The source below is very rudimentary, for brevity's sake. The serial port selection is quite crude. Refer to your configuration and Processing reference for the serial library to get best results.

Note: I've found the serial to be sometimes more prone to errors, especially when loading longer BASIC files. I've sometimes used a few millisecond delay between characters. Also, sometimes resetting the QL helps clear problems, and is recommended if the loading fails. Sometimes it seems the computer gets up on the wrong foot.




import processing.serial.*;
Serial myPort;

void setup()
{
  String portName = Serial.list()[0];
  println(Serial.list());
  myPort = new Serial(this, Serial.list()[0], 2400,'N',8,1.0);
  println("At the QL end:");
  println("BAUD 2400");
  println("LBYTES ser2,address [for binary]");
  println("LOAD ser2z [for basic]");
  println("-------");
  println("Here, activate the window and");
  println("Press s to send binary");
  println("Press b to send basic");
}

void sersend(int b)
{
      print(b+".");
      myPort.write(b); 
}

void bin_send(String fname)
{
  byte bas[] = loadBytes(fname);
  int lenni,lea,leb,lec,a,iad;
  lenni=bas.length;
  lenni--;
  println("LENGTH:"+lenni);
  
  lea=lenni/65536;
  leb=(lenni-(lea*65536))/256;
  lec=(lenni-((lea*65536)+(leb*256)));
  sersend(255);
  sersend(0);
  sersend(lea);
  sersend(leb);
  sersend(lec);
  for(int n=1;n<=10;n++){
    sersend(0);
  }
  for(int i=0;i<=lenni;i++){
    a=int(bas[i]);
    sersend(a);
  }
}

void bas_send(String fname)
{
    byte bas[] = loadBytes(fname);
    int lenni=bas.length;
    int a,iad;
    lenni--;
    for(int i=0;i<=lenni;i++){
      a=int(bas[i]);
      sersend(a);
//the delay may help if the QL does not behave
//delay(5) 

    }
  sersend(26);
}

void keyPressed()
{
    if(key=='s'){bin_send("QLDATA.BIN");}
    if(key=='b'){bas_send("QLBASIC.BAS");}
}

void draw()
{
}


Thursday, 12 September 2013

Canon X-07


A little beauty, this one. The computer is book-sized and fits into a VHS-case sized plastic binder. It offers pretty much what a home micro would have around 1983, except in a very small portable size. The language is Microsoft BASIC, which was state of the art at the time. Well, the memory is not that impressive, only 8K of which roughly 6 are available to BASIC.

Despite the looks the X-07 is not really a scientific calculator. For example, the math symbols are not directly available but behind SHIFT-combinations as on an ordinary micro. It's of course possible to write some calculator software! The BASIC offers very direct access to screen features such as text and bitmap graphics with commands like PSET, LINE, CIRCLE and FONT$ which can be used for the 5x8 user character definition. I suppose for graphing purposes these are fine and to me this is more flexible than the clunky TI-BASIC found in Texas Instruments calculators, even the newer ones.

On the negative side, the connectors are a bit non-standard. For a tinkerer it's nothing, but of course an ordinary RS232 port would have been nice (It's not even that much smaller). Sadly the resolution is very small, 120x32 pixels, and the display is not backlit. Apparently there's a display adapter which would give an 8-colour display on a television. This would make X-07 even more interesting, although then it would no longer be portable.

The Z80-compatible chip is likely to be on the slow side to conserve power, my hunch is 1mhz. (Edit: Nope, it seems the NSC800N variant is 2.5mhz) Printing and graphics commands are quite slow via BASIC. I don't know how long the battery life is, but I'd assume that the display is not that greedy.



What I like about this machine is that the "booting" time is non-existing. The RAM "disk" is permanent as long as the batteries last. The user chooses a suitable portion of the memory for the RAM files, and code snippets can be stored and retrieved via SAVE and LOAD commands. DIR brings up the file list. It's also possible to RUN "filename" to execute a file without loading it into the text memory.

The RAM is battery-backed and it's also possible to put the display to SLEEP and continue later from where you left. There are some interesting possibilities for using this computer to "upload" tiny pieces of data via the RS232, and I might be tempted to try this later. An "autobooting" command can also be created, for running the program in memory, for example. This makes me think the computer is meant to be customized into a variety of one-purpose devices, possibly a controller for industrial machines.

The eight bits between the nybbles. We've seen this before.
Tape options are of course available and using Audacity on my MiniMac I could store and reload a BASIC program. The format seems straightforward enough and if there's nothing about it on the internet I might examine it a bit further. (Edit: Actually, it's all in the manual. Silly me. Also, there's a webpage about the tape formats.)

I feel positive about this tiny computer. The build quality is high and the Canon competence in calculators also shows here. Everything there is, is pretty well made and thought out.


The memory upgrade:

A Toshiba TC5565PL-15 memory chip adds 8K memory, to a total of 16K. The whole system may need resetting before the memory becomes active. The RAMdisk use becomes a bit more reasonable with this expansion.



How to build an RS-232 cable between Canon X-07 and a PC:

Edit: I'd recommend NOT connecting this serial port directly to a Mac/PC! They have a different voltage level.

It is quite fortunate that a piece like the one below can be stuck into the existing port, by ever so slightly twisting the pins. However, the pin order is not standard so a special cable or an adapter needs to be built.


The diagram below shows how to connect between two port types. A cable between two Canons would of course be symmetrical. Note that the numbering in Canon port follows the order in the manual. (1=LTxD, FG, N.C., TxD, RxD, CTS, RTS, SG, VBB) 

The manual also tells the signal level is not standard, but this did not seem to cause problems when connecting between Canon and a Mac. I just went away and tried, although they should not be compatible. I'd be careful. What I see the RS232 in Canon is likely to be TTL level ("5v") whereas serial ports can be 12v. I suspect modern computers and USB/serial adapters may be accommodating, but I'd be wary of connecting different kinds of computers.


The serial port, seen from the outside.

On the Canon end, you do this to set the port:

INIT #1,"COM:",2400,"B"

4800 is the highest speed. The "B" combines the various parity and bit length parameters into a single letter. B seems to work ok with 8 bits, no parity.

After initializing the channel you can:

PRINT #1,"HELLO" to send a string of characters.

...or OUT #1,65 to send characters out.

...or LIST #1 to output the BASIC listing in ASCII.


Some good resources:

The Canon is quite well documented on the net. There seems to be a whole scene focusing on collecting and enthusing about hand-helds, calculators and even digital wrist watch computers.

Here's a page that tells everything you need to know about various peripherals and extension cards:

http://gtello.pagesperso-orange.fr/cx07_e.htm

Programs for creating tape files:

http://www.mvcsys.de/doc/casioutil.html