ruud.baltissen_at_apg.nl
Date: 2009-01-05 13:48:09
Hallo allemaal, Again an update on my project. It still isn't running but at least I know the cause of all my trouble. I never understood how the 1541 exactly handled the BAM and still don't :( For this reason I always replaced the BAM routines by my own. With my own routines almost all common things worked fine but there was always a catch somewhere, like the problems with COPY and SCRATCH I reported before. Saturday I started another try to handle 16 MB disks. In this case I decided to leave the BAM routines "as is" and to solve the problem in another way. Dealing with 16 MB disks means I need a bigger BAM. The idea was to use track 0 for storing the BAM as I cannot use it for regular operations like saving files. So first I persuaded the 1541 to use track 1 as BAM/directory. In this way I found out that, although they should use a pointer stored at $FE85, some routines used an hard coded pointer (LDA #18 instead of LDA $FE85). After replacing these by $FE85, things ran fine. But I lost valuable time to find out why I only had 662 free blocks instead of the usual 664 :( The next step was moving the whole to track 0. This worked out fine although my test program collapsed. Using track 0 means I need four extra bytes in the BAM table. In this case the very first four bytes. And the first three are nomally used for "next directory track", "next directory sector" and "1541 code A". My program reads the directory as a sequentail file and collapsed on the now not existing pointers. Creating, copying and saving of PRGs, sequential and relative files, as well as loading the directory in the normal way, worked fine. I still want to use track 18 / sector 0 (18/0) for storing the label and disk-ID. The 8x50 drives behave in the same way; they only use other tracks to store the BAM and directory. For showing the directory I need to read 18/0, for calculating the number of free blocks I need to read 0/0. The trouble is that the 1541 checks if buffer 4 is already in use. If that is the case, it assumes the BAM is already loaded and skips the loading routine. In the version I am working at now, I reached this point yesterday evening: if I ask for the directory, the 1541 first loads 18/0 for the label and then I tell it load 0/0 to count the free blocks. And that action is skipped with as result 0 free blocks. But I have dealt with this problem in a previous version so I think I can solve it. "Think" because in this previous version I didn't test things to well and ran into serious trouble after having changed to much code :( The main idea is to load the BAM and when 18/0 is needed, to "park" the contents of the buffer on a unused sector on track 0 and to restore it after the action. The problem is that I haven't found all routines needing the label and/or ID yet (and therefor those problems). Next part is for the techies amongst us. For those who understand old Dutch: "Ter leeringh ende vermaek!". When a sector has to be allocated, the routine at $EF90, 'AllocSector', is called. This routine first checks whether the BAM has to be written to the disk or not ($EFF1). Weird thing: the 'FreeSector' routine at $EF5F does NOT call this function, why? Even weirder: at $EF5C, just before FreeSector, you find the call to $EFF1 as if this used to be the original entrance to FreeSector. Both AllocSector and FreeSector then call a routine at $EFCF, which gets the state of the bit in the BAM representing the sector to be allocated, 'GetBitBAM'. GetBitBAM immediatly calls a routine at $F011, 'GetBamField', to find the four bytes in the BAM representing the track where the sector is located. At $F02C the track is compared with two values of a group of four (the last two are for drive 1) called TBAM, found from $029D on. If the track isn't equal to one of the two values, the BAM can be loaded, if not loaded yet. Wanting to be in full control, I thought I could skip these equations. Wrong! When ommiting this check, nothing works anymore. And I haven't found out why yet. If the equations don't work out, a routine at $F05B is called. BTW, this is the only place where this routine is called. In some earlier versions I saved some bytes (and stack space when running) by replacing the original JSR by the routine itself. This routine loads the BAM, if not loaded yet. If loaded, I'm a bit in trouble because in the future I have to deal with more sectors. So I have to convince it yet to load the needed sector in one or another way. F05B calls the routine 'VerifyBamEntry' at $F0A5. At the start the TBAM is used to check whether or not to perform the routine. If the routine is performed, TBAM is cleared. At $F0BE you'll find a puzzling piece of code: it copies 4 bytes from a block of 16 located at $02A1, BAMimage, into the buffer where the BAM is. Which 4 bytes of the firts 8, the other eight are for drive 1, depends on the earlier mentioned equation and the variable UBAM, $029B. Now 4 bytes of the BAM are copied somewhere into this BAMimage and the copied bytes are replaced by zeros. FYI, in an earlier version I ommited the VerifyBamRoutine to save space and the noticed, too late of course, that the BAM was filled with all zeros. Then one of the first two TBAM bytes is filled with the track number. At the end, if there hasn't been tempered with the BAM by another routine, the BAM with those 4 zeros is saved to disk. After calling F05B the variable UBAM is set. Then the pointer BMPNT is set to point to the 4 bytes in use in BAMimage. The control is given back to GetBitBAM where the exact byte and bit are looked up. AllocSector and FreeSector do the rest. Writing the above made even more understand what is going on. But the "why ????". It looks to me as if an airline wants to fly passengers from New York to San Fransico but drops them in Chicago and then sends another plane to fly those passengers from Chicago to San Fransisco. And to make it weirder, the next flight drops the passengers in Dallas and the next one in Chicago again. At least it makes no sense to me. And the weird behaviour around TBAM haven't been explained as well. What is even worse, there must be connections between these weird routine and other routines. Unfortunately I haven't found them :( -- ___ / __|__ / / |_/ Groetjes, Ruud \ \__|_\ \___| URL: Ruud.C64.org De informatie in dit e-mailbericht is vertrouwelijk en uitsluitend bestemd voor de geadresseerde. Wanneer u dit bericht per abuis ontvangt, verzoeken wij u contact op te nemen met de afzender per kerende e-mail. Verder verzoeken wij u in dat geval dit e-mailbericht te vernietigen en de inhoud ervan aan niemand openbaar te maken. Wij aanvaarden geen aansprakelijkheid voor onjuiste, onvolledige dan wel ontijdige overbrenging van de inhoud van een verzonden e-mailbericht, noch voor daarbij overgebrachte virussen. APG Algemene Pensioen Groep NV is gevestigd te Heerlen en is ingeschreven in het handelsregister van de Kamer van Koophandel Limburg onder nummer 14099617 The information contained in this e-mail is confidential and may be privileged. It may be read, copied and used only by the intended recipient. If you have received it in error, please contact the sender immediately by return e-mail; please delete in this case the e-mail and do not disclose it's contents to any person. We don't accept liability for any errors, omissions, delays of receipt or viruses in the contents of this message which arise as a result of e-mail transmission. APG Algemene Pensioen Groep NV is registered in the trade register of the Chamber of Commerce Limburg, The Netherlands, registration number: 14099617 Message was sent through the cbm-hackers mailing list
Archive generated by hypermail pre-2.1.8.