home *** CD-ROM | disk | FTP | other *** search
- C************************************************
- C* *
- C* CPMD2--CP/M TO DEC DISK TRANSLATER *
- C* *
- C* NOTE: MUST BE COMPILED '/NOSWAP' *
- C* *
- C* THIS IS A SHORT VERSION OF CPMDEC, FOR USE *
- C* WHERE THE PROGRAM MUST BE HAND ENTERED. *
- C* TYPE THIS FILE INTO YOUR DEC SYSTEM, *
- C* OMITTING THE COMMENTS. THEN COMPILE IT, *
- C* THE RESULT WILL BE A SHORT VERSION WHICH *
- C* WILL ONLY READ CPMDEC FROM THE DISK. *
- C* YOU MAY THEN COMPILE CPMDEC FOR LATER USE.*
- C* *
- C* RUSS BAKKE 02-18-83 *
- C* *
- C************************************************
- C
- PROGRAM CPMD2
- C
- BYTE DIR(32,64),CNAME(12),DNAME(12)
- COMMON DIR
- DATA DNAME/ 'D','K','0','C','P','M','D','E','C',
- + 'F','O','R'/
- DATA CNAME/ 'C','P','M','D','E','C',' ',' ','F','O','R',0/
- C
- TYPE 100
- 100 FORMAT (1X,'CP/M TRANSLATER BOOTSTRAP, V1.0'//
- + 1X,'INSERT CP/M DISK IN DY1: AND PRESS RETURN'/)
- ACCEPT 104,IWANT
- 104 FORMAT (1A1)
- C
- C OPEN CP/M DISK AS NON-FILE STRUCTURED DEVICE:
- CALL DSKOPN(ICHAN)
- CALL GETDIR(ICHAN)
- C
- C LOOKUP CNAME IN DISK DIR
- CALL FIND(CNAME,0,IENTRY)
- IF (IENTRY .NE. -1) GOTO 32 !OK
- 31 TYPE *,'FILE NOT FOUND'
- GOTO 90
- C
- C GET DEC NAME & OPEN
- 32 CALL DECOPN(DNAME,IDCHAN)
- C READ FILE AND WRITE TO DEC
- CALL CPYFIL(IENTRY,CNAME,ICHAN,IDCHAN)
- C
- C CLOSE
- 90 CALL ICLOSE (ICHAN)
- CALL IFREEC (ICHAN)
- CALL EXIT
- END
- C
- SUBROUTINE DSKOPN (IDCH)
- C****************************************************
- C* *
- C* OPEN FLOPPY DISK DRIVE 1 AS NON-FILE *
- C* STRUCTURED DEVICE; RETURN CHANNEL NO. IN IDCH. *
- C* *
- C* RUSS BAKKE 02-10-83 *
- C* *
- C****************************************************
- C
- REAL*4 DISK1
- DATA DISK1 /3RDY1 /
- C
- C FETCH HANDLER, OPEN A CHANNEL, LOOKUP DEVICE
- IF (IFETCH(DISK1) .NE. 0) STOP 'IFETCH ERROR
- + IN DSKOPN'
- IDCH=IGETC()
- IF(IDCH.LT.0) STOP' NO CHANNEL AVAILABLE'
- C
- IRET = LOOKUP(IDCH,DISK1)
- IF (IRET .GE. 0) GOTO 10
- C
- C LOOKUP FAILURE
- TYPE *,'LOOKUP FAILURE TYPE ',IRET
- STOP
- C
- 10 RETURN
- END
- C
- SUBROUTINE GETDIR(ICHAN)
- C****************************************************
- C* *
- C* READ DIRECTORY OF CP/M DISK. *
- C* *
- C* THE CP/M DISK USES TRACKS 0 AND 1 FOR SYSTEM *
- C* TRACKS; WE MAY IGNORE THEM. THE DIRECTORY IS *
- C* 2K OR 16 SECTORS, STARTING ON TRACK 2. *
- C* *
- C* RUSS BAKKE 05-06-82 *
- C* *
- C****************************************************
- C
- BYTE DIR(32,64)
- COMMON DIR
- C
- DO 80 INDEX=1,16
- ISECTR=INDEX
- CALL DOSEC(2,ISECTR,DIR(1,4*(ISECTR-1)+1),ICHAN)
- 80 C O N T I N U E
- RETURN
- END
- C
- SUBROUTINE DOSEC(ITRK,ISEC,BUFF,ICHAN)
- C****************************************************
- C* *
- C* READ LOGICAL SECTOR 'ISEC', TRACK 'ITRK', TO *
- C* 'BUFF' (128 BYTES), FROM CHANNEL 'ICHAN'. *
- C* *
- C* RUSS BAKKE 02-18-83 *
- C* *
- C****************************************************
- C
- BYTE BUFF(128),MYBUFF(130)
- INTEGER ITABLE(26)
- DATA ITABLE /1,7,13,19,25,5,11,17,23,3,9,15,21,2,8,
- + 14,20,26,6,12,18,24,4,10,16,22/
- C ITABLE IS THE CP/M SECTOR INTERLEAVE TABLE (26 SECTORS PER TRACK)
- C PHYSICAL SECTOR # [1..26] = ITABLE(LOGICAL SECTOR # [1..26])
- C
- IRET=ISPFNW("377,ICHAN,ITRK,MYBUFF,ITABLE(ISEC))
- C
- C THE ISPFNW CALL IS AS FOLLOWS:
- C IRET=ISPFNW(FUNC,ICHAN,ITRK,BUFF,SECTOR)
- C FUNC="377 FOR READ, "376 FOR WRITE
- C ICHAN=CHANNEL #, FROM LOOKUP
- C ITRK=ABSOLUTE PHYSICAL TRACK #, 0..76
- C SECTOR=ABSOLUTE PHYSICAL SECTOR #, 1..26
- C BUFF=128 BYTE BUFFER
- C IRET RETURNS:
- C 0 NORMAL
- C 1 EOF
- C 2 HARDWARE ERROR
- C 3 CHANNEL NOT OPEN
- C
- IF (IRET .EQ. 0) GOTO 40
- 30 TYPE 100,RW,ITRK,ISEC
- 100 FORMAT (1X,A,2X,'TRACK: ',I3,' LOG. SECTOR: ',I3)
- IF (IRET .EQ. 1) STOP 'CHANNEL EOF IN DOSEC'
- IF (IRET .EQ. 2) STOP 'HARDWARE ERROR IN DOSEC'
- IF (IRET .EQ. 3) STOP 'CHANNEL NOT OPEN IN DOSEC'
- STOP 'ERROR IN DOSEC'
- C
- C WE MUST READ INTO 130 BYTE BUFFER, BECAUSE ISPFNW READS
- C LEADING 0 WORD INTO BUFFER. (THIS IS DOCUMENTED IN THE
- C SOFTWARE SUPPORT MANUAL BUT NOT IN THE PROGRAMMER'S REFERENCE).
- 40 DO 45 I=1,128
- BUFF(I) = MYBUFF(I+2)
- 45 C O N T I N U E
- RETURN
- END
- C
- SUBROUTINE DECOPN(FNAME,IDCHAN)
- C**************************************************
- C* *
- C* OPEN A DEC FILE FNAME, RETURNING CHANNEL *
- C* NUMBER IN IDCHAN. *
- C* *
- C* RUSS BAKKE 02-18-83 *
- C* *
- C**************************************************
- C
- BYTE FNAME(12)
- REAL*8 FSPEC
- C
- C GET A CHANNEL
- IDCHAN=IGETC()
- IF(IDCHAN .LT. 0) STOP' NO CHANNEL AVAILABLE'
- C
- C CONVERT FNAME TO RADIX 50
- IDUM=IRAD50(12,FNAME,FSPEC)
- C
- IRET=IENTER(IDCHAN,FSPEC,-1)
- IF (IRET .GE. 0) GOTO 90
- C IENTER ERRORS ARE:
- C -1: CHANNEL ALREADY OPEN
- C -2: NO SPACE AVAILABLE
- C -3: DEVICE IN USE
- C -4: FILE EXISTS AND IS PROTECTED
- C -5: CASSETTE ONLY
- TYPE *,'IENTER FAILURE TYPE ',IRET
- STOP
- C
- 90 RETURN
- END
- C
- SUBROUTINE FIND(CNAME,EXT,IENTRY)
- C****************************************************
- C* *
- C* FIND CP/M FILE NAMED CNAME IN DIRECTORY (IN *
- C* DIR, PASSED IN COMMON), EXTENT 'EXT'; RETURN *
- C* DIRECTORY ENTRY NUMBER IN IENTRY. *
- C* *
- C* RUSS BAKKE 05-11-82 *
- C* *
- C****************************************************
- C
- BYTE DIR(32,64),CNAME(12)
- INTEGER EXT
- COMMON DIR
- C
- DO 44 IENTRY=1,64
- IF (DIR(1,IENTRY) .EQ. "345) GOTO 44 !EMPTY, SKIP
- DO 42 ICHAR=2,12
- IF (DIR(ICHAR,IENTRY) .NE. CNAME(ICHAR-1)) GOTO 44
- 42 C O N T I N U E
- C FALL THROUGH MEANS A MATCH
- IF (DIR(13,IENTRY) .EQ. EXT) GOTO 90 !FOUND IT
- C
- 44 C O N T I N U E
- C FALL THROUGH MEANS NO MATCH FOUND
- IENTRY=-1
- 90 RETURN
- END
- C
- SUBROUTINE CPYFIL(IENTRY,CNAME,ICHAN,IDCHAN)
- C*************************************************
- C* *
- C* COPY CP/M FILE (ICHAN) TO DEC FILE (IDCHAN). *
- C* CP/M DIRECTORY ENTRY IS 'IENTRY'. *
- C* CLOSE DEC CHANNEL (IDCHAN) WHEN FINISHED. *
- C* *
- C* RUSS BAKKE 02-18-83 *
- C* *
- C*************************************************
- C
- BYTE DIR(32,64),DBUFF(1024),CNAME(12)
- COMMON DIR
- C
- IDBLK=0 !DISK BLOCK TO WRITE
- IEXT=0 !FIRST EXTENT
- C
- 8 ICLU=1 !FIRST CLUSTER
- ISIZE=DIR(16,IENTRY)
- IF (ISIZE .LT. 0) ISIZE=ISIZE+256
- IF (ISIZE .EQ. 128) ISIZE=129 !DON'T LET IT COUNT OUT
- 10 IF (ISIZE .EQ. 0) GOTO 90
- IBLK=DIR(16+ICLU,IENTRY)
- IF (IBLK .LT. 0) IBLK=IBLK+256
- C (PROBLEM HERE, IS WE GET SIGN EXTENSION ON READING BYTE
- C VALUE INTO INTEGER VARIABLE)
- IF (IBLK .EQ. 0) GOTO 90 !THAT'S ALL
- C
- C NEED TO READ 'IBLK' 1K CLUSTER (8 SECTORS)
- C
- C CONVERT IBLK TO STARTING SECTOR # AND TRACK #
- C MULTIPLY BY 8 AND REDUCE MODULO 26
- ITEMP=8*IBLK
- ISTTRK=ITEMP/26
- ISTART=ITEMP-26*ISTTRK+1
- ISTTRK=ISTTRK+2 !SKIP SYSTEM TRACKS
- C
- DO 60 ISECTR=0,7
- ITEMP=ISTART+ISECTR
- ITRK=ISTTRK
- IF (ITEMP .LE. 26) GOTO 30
- ITEMP=ITEMP-26
- ITRK=ITRK+1
- 30 CALL DOSEC(ITRK,ITEMP,DBUFF(128*ISECTR+1),ICHAN)
- ISIZE=ISIZE-1
- IF (ISIZE .LE. 0) GOTO 62
- 60 C O N T I N U E
- C
- C NOW WRITE BUFF TO IDCHAN
- C SEARCH BUFFER FOR CTL-Z (EOF)
- 62 DO 65 INDEX=1,1024
- IF (DBUFF(INDEX) .EQ. 26) GOTO 75
- 65 C O N T I N U E
- C
- 70 IRET=IWRITW(512,DBUFF,IDBLK,IDCHAN)
- IDBLK=IDBLK+2
- C IWRITW RETURNS:
- C -1: EOF
- C -2: HARDWARE ERROR
- C -3: CHANNEL NOT OPEN
- C
- IF (IRET .LT. 0) GOTO 95
- ICLU=ICLU+1
- IF (ICLU .LT. 17) GOTO 10 !NEXT SEGMENT
- C
- C NOW SEE IF WE HAVE ANOTHER EXTENT
- IEXT=IEXT+1
- CALL FIND(CNAME,IEXT,IENTRY)
- IF (IENTRY .NE. -1) GOTO 8 !NEXT EXTENT
- GOTO 90
- C
- C HAVE EOF AT "INDEX"
- 75 DO 78 INDEX1=INDEX,1024
- DBUFF(INDEX1)=0 !NULL FILL
- 78 C O N T I N U E
- IF (INDEX .GT. 512) GOTO 84
- C
- C HAVE PARTIAL BUFFER--WRITE IT OUT.
- 83 IRET=IWRITW(256,DBUFF,IDBLK,IDCHAN)
- IDBLK=1
- GOTO 86
- C
- 84 IRET=IWRITW(512,DBUFF,IDBLK,IDCHAN)
- IDBLK=2
- 86 IF (IRET .LT. 0) GOTO 95
- 90 IF (IDBLK .EQ. 0) GOTO 94
- CALL ICLOSE(IDCHAN)
- 92 CALL IFREEC(IDCHAN)
- RETURN
- C
- C FILE OF 0 LENGTH, EAT IT.
- 94 CALL PURGE(IDCHAN)
- GOTO 92
- C
- 95 TYPE *,'WRITE ERROR IN CPYFIL, TYPE ',IRET
- STOP
- END
-