Here is the programming algorithm from the datasheet (only extracts or summaries)
File : 135891_DS.pdf
Am29F040B
4 Megabit (512K x 8-bit)
CMOS 5.0 Volt-only, Uniform Sector Flash Memory
it explains that the memory is diided in 8 sectors of 64Kb
Programming is done as a 4 bus-cycle operation : 2 unlock cycles, program setup command then address+data written...
A bit cannot be programmed from a "0" back to a "1"... Only an erase operation can convert a "0" to a "1"...
Commands :
Read
Address = AAA , chip read
Reset
Address=XXX Data = F0, chip write
Autoselect
read manufacture ID, device ID and sector protect... not relevant here
Program
1) address=555 Data=AA chip write
2) Address=2AA Data=55, chip write
3) Address=555 Data=A0, chip write
4) Adress=adr, Data=d, chip write
Chip erase
1) address=555 Data=AA chip write
2) Address=2AA Data=55, chip write
3) Address=555 Data=80, chip write
4) address=555 Data=AA chip write
5) Address=2AA Data=55, chip write
6) Address=555 Data=10, chip write
Sector Erase
1) address=555 Data=AA chip write
2) Address=2AA Data=55, chip write
3) Address=555 Data=80, chip write
4) address=555 Data=AA chip write
5) Address=2AA Data=55, chip write
6) Address=Sector Data=30, chip write
Sector : Address bits 16-18 used to select sector
Status readback
While writting in progress, a read in the programmed (or erased) area will return the negation of Data bit 7 on the D7 line.When write is complete, D7 line will return to the Data bit 7.
While writting in progress, successive reads to an address will return toggling value on D6 (alternating 0 and 1). when writting (or erase) complete, the actual data wil be returned
D2 behave like D6 during erase cycles except that if erase is suspended, D2 will continue to toggle while D6 stops
D5 signals an error (while either D7 inverted or D2/D6 is toggling). If it goes to 1, it means that an error happenned (timeout or trying to set from 0 to 1 in write)
If D5 goes to 1, you need to read data again and check if it's correct as D7/D2/D6 don't change at same time than D5 so it could be that the process ended and that the data has D5 set to 1
D3 goes to 1 when the erase cycle starts. Before it goes to 1, additionnal erase sector commandes may be sent (<50µs).
---------------------------------------------
So, in order to use these info, we have to be sure that both the address and data line match between Spectrum and DivIDE+. It's also needed to issue commands to control port to set up high address-bits (as only A0-A13 are routed in programming mode)
My guess is that a write should be done by using
OUT 23,101 101 01b LD (00 01 0101 0101 0101b),10101010b (Out 101 = command, 101 01 are top bits, write 00 = rom 16K, 01 0101 0101 0101 = bottom bits)
OUT 23,101 010 10b LD (00 10 1010 1010 1010b),01010101b
OUT 23,101 101 01b LD (00 01 0101 0101 0101b),10100000b (Write command)
OUT 23 101 xxxxx LD (00xx xxxx xxxx xxxx),data (xxxx = address
the use LD A,(00xx xxxx xxxx xxxx xxxx) to read the status and either check bit 7 (complement of bit 7 of data until end of programmation) or bit 6 (toggling until end of programmation)
it's only a guess, I've not tested this and I'd need to first dump the Flash using my flash reader before doing any test (and, well, I'd also need to have more time available).
I don't know if this can be of any use to anyone... An "official" algorithm (and/or code sample) from you would be welcome.