Files
SyncHome/trunk/workspace/SharpTools/Sources/bin2tap.c
2023-03-13 08:36:51 +00:00

1950 lines
54 KiB
C

/* Textcoding Unicode (UTF-8, no BOM), End of Line Windows (CRLF)
bin2wav.c
V 1.3 www.pocketmuseum.com
2011-12-05 V 1.4 Manfred NOSSWITZ
Changed to ANSI-C e.g. strupr()
Command line parser changed to getopt().
Quiet mode added.
32bit compilation with gcc (tdm64-1) 4.6.1 (WindowsXP-prof [32bit]): gcc -pedantic -m32 -o xxx xxx.c
32bit compilation with gcc-4_5-branch revision 167585 (OpenSUSE 11.4 [32bit]): gcc -pedantic -m32 -o xxx xxx.c
64bit compilation with gcc (tdm64-1) 4.6.1 (Windows7-prof [64bit]): gcc -pedantic -m64 -o xxx xxx.c
64bit compilation with gcc-4_5-branch revision 167585 (OpenSUSE 11.4 [64bit]): gcc -pedantic -m64 -o xxx xxx.c
For testing PC-1402 was available only
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <getopt.h> /* Command line parser getopt(). */
#define ERR_OK 0
#define ERR_NOK -1
#define TYPE_NOK 0
#define TYPE_BIN 1
#define TYPE_IMG 2
#define IDENT_UNKNOWN 0x00
#define IDENT_OLD_BAS 0x20
#define IDENT_OLD_PAS 0x21
#define IDENT_OLD_BIN 0x26
#define IDENT_NEW_BAS 0x70
#define IDENT_NEW_PAS 0x71
#define IDENT_EXT_BAS 0x72
#define IDENT_EXT_PAS 0x73
#define IDENT_NEW_BIN 0x76
#define IDENT_PC1211 0x80
#define IDENT_PC1500 0x0A
#define IDENT_PC15_BIN 0xA0
#define IDENT_PC15_BAS 0xA1
#define ORDER_STD 0
#define ORDER_INV 1
#define MODE_B22 0
#define MODE_B21 1
#define MODE_B20 2
#define MODE_B19 3
#define MODE_B17 4
#define MODE_B16 5
#define MODE_B14 6
#define MODE_B13 7
#define BASE_FREQ1 4000
#define BASE_FREQ2 2500
#define CHAR_SPACE 0x20
#define CHAR_DOT 0x2E
#define CHAR_COLON 0x3A
#define CHAR_SLASH 0x5C
#define CHAR_UNDERSCORE 0x5F
#define cLPF 129 /* Constant value for max. Length of PathFilenames */
/* used types */
/* char; */
typedef unsigned char uchar;
/* int; */
typedef unsigned int uint;
/* long; */
typedef unsigned long ulong;
char argP[cLPF] = "" ;
uint Qcnt = 0 ;
typedef struct {
FILE* ptrFd ;
ulong ident ;
ulong count ;
ulong sum ;
} FileInfo ;
typedef struct {
ulong nb1 ;
ulong nb2 ;
} ModeInfo ;
static ModeInfo Mode[] = {
{ 6, 6 }, { 5, 6 }, { 5, 5 }, { 4, 5 },
{ 1, 6 }, { 1, 5 }, { 1, 3 }, { 1, 2 }
} ;
static char* bit[] = {
"\255\255\0\0\255\255\0\0\255\255\0\0\255\255\0\0",
"\255\0\255\0\255\0\255\0\255\0\255\0\255\0\255\0"
} ;
static ulong CodeOld[] = {
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x11,0x14,0x12,0x15,0x19,0x16,0x1F,0x11,
0x30,0x31,0x37,0x35,0x1B,0x36,0x4A,0x38,
0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,
0x48,0x49,0x1D,0x1C,0x33,0x34,0x32,0x13,
0x1E,0x51,0x52,0x53,0x54,0x55,0x56,0x57,
0x58,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,
0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,
0x68,0x69,0x6A,0x11,0x11,0x11,0x39,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11,
0x19,0x11,0x1A,0x11,0x11,0x11,0x11,0x11,
0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11
} ;
void CvShortToStringI (uint value,
char* ptrStr)
{
uint tmp ;
/* Convert the short value into a String with msb first (INTEL) */
tmp = value & 0xFF ;
*ptrStr ++ = (char) tmp ;
tmp = value >> 8 ;
*ptrStr ++ = (char) tmp ;
*ptrStr = 0 ;
}
void CvLongToStringI (ulong value,
char* ptrStr)
{
ulong tmp ;
/* Convert the 32bit value into a String with msb first (INTEL) */
tmp = value & 0xFF ;
*ptrStr ++ = (char) tmp ;
tmp = (value >> 8) & 0xFF ;
*ptrStr ++ = (char) tmp ;
tmp = (value >> 16) & 0xFF ;
*ptrStr ++ = (char) tmp ;
tmp = value >> 24 ;
*ptrStr ++ = (char) tmp ;
*ptrStr = 0 ;
}
/* String-change UPPER */
char *strupr( char *string )
{
int i = 0;
while ( ( string[i] = toupper( string[i] ) ) != '\0') i++;
return string;
}
int WriteStringToFile (char* ptrStr,
FILE** ptrFd)
{
int error ;
error = fputs (ptrStr, *ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
}
else {
error = ERR_OK ;
}
return (error);
}
int WriteLongToFile (ulong value,
FILE** ptrFd)
{
char str[10] ;
int ii ;
int error ;
CvLongToStringI (value, str) ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
error = fputc (str[ii], *ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
}
return (error);
}
int WriteShortToFile (ulong value,
FILE** ptrFd)
{
char str[10] ;
int ii ;
int error ;
CvShortToStringI (value, str) ;
for ( ii = 0 ; ii < 2 ; ii++ ) {
error = fputc (str[ii], *ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
}
return (error);
}
int ReadFileLength (ulong* ptrLen,
FILE** ptrFd)
{
long nbByte ;
int error ;
do {
*ptrLen = 0 ;
/* Seek to the end of the source file */
error = fseek (*ptrFd, 0, SEEK_END) ;
if (error != ERR_OK) {
printf ("%s: Can't seek the file\n", argP) ;
break ;
}
/* Get the length of the source file */
nbByte = ftell (*ptrFd) ;
if (nbByte == ERR_NOK) {
printf ("%s: Can't ftell the file\n", argP) ;
error = ERR_NOK ;
break ;
}
/* Seek to the begining of the source file */
error = fseek (*ptrFd, 0, SEEK_SET) ;
if (error != ERR_OK) {
printf ("%s: Can't seek the file\n", argP) ;
break ;
}
if (nbByte == 0) {
printf ("%s: Source file is empty\n", argP) ;
error = ERR_NOK ;
break ;
}
*ptrLen = nbByte ;
} while (0) ;
return (error);
}
int LengthAndIdentOfBinTap (ulong type,
ulong pcId,
ulong nbByte,
ulong nbSync,
ulong* ptrIdent,
ulong* ptrSamp)
{
ulong ident ;
ulong nbSamp ;
int error ;
do {
error = ERR_OK ;
switch (pcId) {
case 1500 :
if (type == TYPE_BIN) {
/* Footer = 3 bytes : sum, 0x55 */
ident = IDENT_PC15_BIN ;
nbSamp = 3 ;
}
else {
/* Footer = 4 bytes : 0xFF, sum, 0x55 */
ident = IDENT_PC15_BAS ;
nbSamp = 4 ;
}
/* Header = 42, Lead = nbByte + 2 * (nbByte / 80) */
/* One Byte = 22 bits, each Bit = 16 Samples */
/* One Sync = one Bit = 16 Samples (2500 Hz) */
/* Ident = 11 bits, 3 gaps of 70 bits */
nbSamp = nbSamp + 42 + nbByte + 2 * (nbByte / 80) ;
nbSamp = nbSamp * 22 * 16 ;
nbSamp = nbSamp + (nbSync * 16) ;
nbSamp = nbSamp + (221 * 16) ;
break ;
case 1245 :
case 1251 :
if (type == TYPE_BIN) {
ident = IDENT_OLD_BIN ;
nbSamp = 1 + (2 * 9) ; /* Header = 19 Byte */
}
else {
ident = IDENT_OLD_BAS ;
nbSamp = 1 + 9 ; /* Header = 10 Byte */
}
/* Footer = 1, Lead = nbByte + (nbByte / 8) */
/* One Byte = 19 bits, each Bit = 16 Samples */
/* One Sync = one Bit = 16 Samples (4000 Hz) */
nbSamp = nbSamp + 1 + nbByte + (nbByte / 8) ;
nbSamp = nbSamp * 19 * 16 ;
nbSamp = nbSamp + (nbSync * 16) ;
break ;
case 1261 :
case 1350 :
case 1360 :
case 1401 :
case 1402 :
case 1403 :
case 1450 :
case 1475 :
if (type == TYPE_BIN) {
ident = IDENT_NEW_BIN ;
nbSamp = (1 + (2 * 9)) * 16 * 16 ; /* Header = 19 Byte16 */
}
else {
if ( (pcId == 1360) ||
(pcId == 1475) )
ident = IDENT_EXT_BAS ;
else
ident = IDENT_NEW_BAS ;
nbSamp = (1 + 9) * 16 * 16 ; /* Header = 10 Byte16 */
}
/* Footer = 3 Byte13 */
/* Lead = (nbByte + (nbByte / 120)) Byte13 */
/* Byte = 16 or 13 bits, Bit = 16 Samples */
/* Sync = one Bit = 16 Samples (4000 Hz) */
/* there are 2bits more HIGH at the end of transmission (at least for PC-1402) M. NOSSWITZ */
nbSamp = nbSamp + ((nbByte + 3 + (nbByte / 120)) * 13 * 16) ;
nbSamp = nbSamp + (nbSync * 16) ;
nbSamp = nbSamp + 32 ;
break ;
default :
nbSamp = 0 ;
ident = 0 ;
break ;
}
*ptrIdent = ident ;
*ptrSamp = nbSamp ;
} while (0) ;
return (error);
}
int WriteHeadToTap (ulong nbSamp,
ulong freq,
FileInfo* ptrFile)
{
/* int error ;
do {
error = WriteStringToFile ("RIFF", &ptrFile->ptrFd) ;
if (error != ERR_OK) break ;
error = WriteLongToFile ((nbSamp + 36), &ptrFile->ptrFd) ;
if (error != ERR_OK) break ;
error = WriteStringToFile ("WAVEfmt ", &ptrFile->ptrFd) ;
if (error != ERR_OK) break ;
error = WriteLongToFile (0x10, &ptrFile->ptrFd) ;
if (error != ERR_OK) break ;
error = WriteShortToFile (1, &ptrFile->ptrFd) ; // PCM
if (error != ERR_OK) break ;
error = WriteShortToFile (1, &ptrFile->ptrFd) ; // Mono
if (error != ERR_OK) break ;
error = WriteLongToFile (freq, &ptrFile->ptrFd) ; // Samp Freq
if (error != ERR_OK) break ;
error = WriteLongToFile (freq, &ptrFile->ptrFd) ; // Byte / sec
if (error != ERR_OK) break ;
error = WriteShortToFile (1, &ptrFile->ptrFd) ; // Byte / Samp x Chan
if (error != ERR_OK) break ;
error = WriteShortToFile (8, &ptrFile->ptrFd) ; // Bit / Samp
if (error != ERR_OK) break ;
error = WriteStringToFile ("data", &ptrFile->ptrFd) ;
if (error != ERR_OK) break ;
error = WriteLongToFile (nbSamp, &ptrFile->ptrFd) ; // Nb Samples
if (error != ERR_OK) break ;
} while (0) ;
return (error); */
return ERR_OK;
}
int WriteBitToWav (ulong value,
FileInfo* ptrFile)
{
/* int ii ;
int error ;
uchar outb;
for ( ii = 0 ; ii < 16 ; ii++ ) {
if (bit[value][ii]) outb = 0xDA; else outb = 0x25;
error = fputc (outb, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
}
return (error); */
return ERR_OK;
}
int WriteSyncToTap (int nbSync,
FileInfo* ptrFile)
{
/* int ii ;
int error ;
do {
// Write the Synchro patern
for ( ii = 0 ; ii < nbSync ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ;
return (error); */
return ERR_OK;
}
int WriteQuaterToTap (ulong value,
ulong nbBits,
FileInfo* ptrFile)
{
ulong tmp ;
int ii ;
int error ;
do {
error = fputc (0xF0 | value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/* do {
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToTap (0, ptrFile) ;
else
error = WriteBitToTap (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < nbBits ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteToTap (ulong value,
ulong order,
ulong mode,
FileInfo* ptrFile)
{
ulong lsq ;
ulong msq ;
int error ;
do {
lsq = value & 0x0F ;
msq = (value >> 4) & 0x0F ;
if (order == ORDER_INV) {
error = fputc (0xF0 | lsq, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
error = fputc (0xF0 | msq, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
/* error = WriteQuaterToWav (lsq, Mode[mode].nb1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteQuaterToWav (msq, Mode[mode].nb2, ptrFile) ;
if (error != ERR_OK) break ; */
}
else {
error = fputc (0xF0 | msq, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
error = fputc (0xF0 | lsq, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
/* error = WriteQuaterToWav (msq, Mode[mode].nb1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteQuaterToWav (lsq, Mode[mode].nb2, ptrFile) ;
if (error != ERR_OK) break ; */
}
} while (0) ;
return (error);
}
int WriteByteSumToTap (ulong value,
ulong order,
ulong mode,
FileInfo* ptrFile)
{
int error ;
do {
error = WriteByteToTap (value, order, mode, ptrFile) ;
if (error != ERR_OK) break ;
ptrFile->count = ptrFile->count + 1;
switch (mode) {
case MODE_B22 :
if ( (ptrFile->count % 80) == 0) {
}
break ;
case MODE_B21 :
case MODE_B20 :
case MODE_B19 :
if ( (ptrFile->count % 8) == 0) {
}
break ;
case MODE_B17 :
case MODE_B16 :
case MODE_B14 :
case MODE_B13 :
if ( (ptrFile->count % 120) == 0) {
}
break ;
default :
printf ("%s: Unknown Mode\n", argP) ;
break ;
}
} while (0) ;
return (error);
}
int WriteIdentToB22Tap (ulong value,
FileInfo* ptrFile)
{
ulong tmp ;
int ii ;
int error ;
do {
error = fputc (0xF0 | value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/*
do {
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 6 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteToB22Tap (ulong value,
FileInfo* ptrFile)
{
int error ;
do {
error = fputc (value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/* ulong tmp ;
int ii ;
int error ;
do {
error = Write
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 6 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 4 ; ii < 8 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 6 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteToB19Wav (ulong value,
FileInfo* ptrFile)
{
int error ;
do {
error = fputc (value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/* ulong tmp ;
int ii ;
int error ;
do {
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 4 ; ii < 8 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 5 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteToB16Wav (ulong value,
FileInfo* ptrFile)
{
int error ;
do {
error = fputc (value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/* ulong tmp ;
int ii ;
int error ;
do {
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 4 ; ii < 8 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 5 ; ii++ ) {
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteToB13Wav (ulong value,
FileInfo* ptrFile)
{
int error ;
do {
error = fputc (value, ptrFile->ptrFd) ;
if (error == EOF) {
printf ("%s: Can't write in the file\n", argP) ;
error = ERR_NOK ;
break ;
}
else
error = ERR_OK ;
} while (0);
/* ulong tmp ;
int ii ;
int error ;
do {
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 4 ; ii < 8 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteBitToWav (0, ptrFile) ;
if (error != ERR_OK) break ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
tmp = 1 << ii ;
if ( (value & tmp) == 0 )
error = WriteBitToWav (0, ptrFile) ;
else
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
} while (0) ; */
return (error);
}
int WriteByteSumToB22Tap (ulong value,
FileInfo* ptrFile)
{
ulong cnt ;
ulong sum ;
ulong tmpL ;
int error ;
do {
cnt = ptrFile->count ;
sum = ptrFile->sum ;
/* Write the byte */
error = WriteByteToB22Tap (value, ptrFile) ;
if (error != ERR_OK) break ;
/* Update the SumCheck and the Byte Counter */
sum = sum + value ;
cnt = cnt + 1 ;
if (cnt >= 80) {
/* Write the SumCheck */
tmpL = (sum >> 8) & 0xFF ;
error = WriteByteToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = sum & 0xFF ;
error = WriteByteToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
cnt = 0 ;
sum = 0 ;
}
ptrFile->count = cnt ;
ptrFile->sum = sum ;
} while (0) ;
return (error);
}
int WriteByteSumToB19Wav (ulong value,
FileInfo* ptrFile)
{
ulong cnt ;
ulong sum ;
int error ;
do {
cnt = ptrFile->count ;
sum = ptrFile->sum ;
/* Write the byte */
error = WriteByteToB19Wav (value, ptrFile) ;
if (error != ERR_OK) break ;
/* Update the SumCheck */
sum = sum + ((value & 0xF0) >> 4) ;
if (sum > 0xFF)
sum = (sum + 1) & 0xFF ;
sum = (sum + (value & 0x0F)) & 0xFF ;
/* Update the Byte Counter */
cnt = cnt + 1 ;
if ( (cnt % 8) == 0 ) {
/* Write the SumCheck */
error = WriteByteToB19Wav (sum, ptrFile) ;
if (error != ERR_OK) break ;
if (cnt >= 80) {
cnt = 0 ;
sum = 0 ;
}
}
ptrFile->count = cnt ;
ptrFile->sum = sum ;
} while (0) ;
return (error);
}
int WriteByteSumToB16Wav (ulong value,
FileInfo* ptrFile)
{
ulong cnt ;
ulong sum ;
int error ;
do {
cnt = ptrFile->count ;
sum = ptrFile->sum ;
/* Write the byte */
error = WriteByteToB16Wav (value, ptrFile) ;
if (error != ERR_OK) break ;
/* Update the SumCheck */
sum = sum + ((value & 0xF0) >> 4) ;
if (sum > 0xFF)
sum = (sum + 1) & 0xFF ;
sum = (sum + (value & 0x0F)) & 0xFF ;
/* Update the Byte Counter */
cnt = cnt + 1 ;
if (cnt >= 8) {
/* Write the SumCheck */
error = WriteByteToB16Wav (sum, ptrFile) ;
if (error != ERR_OK) break ;
cnt = 0 ;
sum = 0 ;
}
ptrFile->count = cnt ;
ptrFile->sum = sum ;
} while (0) ;
return (error);
}
int WriteByteSumToB13Wav (ulong value,
FileInfo* ptrFile)
{
ulong cnt ;
ulong sum ;
int error ;
do {
cnt = ptrFile->count ;
sum = ptrFile->sum ;
/* Write the byte */
error = WriteByteToB13Wav (value, ptrFile) ;
if (error != ERR_OK) break ;
/* Update the SumCheck */
sum = sum + ((value & 0xF0) >> 4) ;
if (sum > 0xFF)
sum = (sum + 1) & 0xFF ;
sum = (sum + (value & 0x0F)) & 0xFF ;
/* Update the Byte Counter */
cnt = cnt + 1 ;
if (cnt >= 120) {
/* Write the SumCheck */
error = WriteByteToB13Wav (sum, ptrFile) ;
if (error != ERR_OK) break ;
cnt = 0 ;
sum = 0 ;
}
ptrFile->count = cnt ;
ptrFile->sum = sum ;
} while (0) ;
return (error);
}
int WriteHeadToB22Tap (char* ptrName,
ulong addr,
ulong size,
ulong type,
FileInfo* ptrFile)
{
int ii ;
ulong len ;
ulong tmpL ;
char tmpS[20] ;
int error ;
do {
/* Search the length */
tmpL = strlen (ptrName) ;
if (tmpL > 16)
tmpL = 16 ;
for ( ii = 0 ; ii < tmpL ; ii++ )
tmpS[ii] = ptrName[ii] ;
for ( ii = tmpL ; ii < 16 ; ii++ )
tmpS[ii] = 0 ;
if (Qcnt == 0) printf ("Save name : %s\n", tmpS) ;
/* Write the Header */
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
for ( ii = 0x10 ; ii < 0x18 ; ii++ ) {
error = WriteByteSumToB22Tap (ii, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
/* Write the first Sub-Ident */
if (type == TYPE_BIN)
tmpL = 0x00 ;
else
tmpL = 0x01 ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the Name */
for ( ii = 0 ; ii < 16 ; ii++ ) {
error = WriteByteSumToB22Tap (tmpS[ii], ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
/* Write 9 null bytes */
for ( ii = 0 ; ii < 9 ; ii++ ) {
error = WriteByteSumToB22Tap (0, ptrFile) ;
if (error != ERR_OK) break ;
}
if (error != ERR_OK) break ;
/* Write the Addresse */
tmpL = (addr >> 8) & 0xFF ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = addr & 0xFF ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the Buffer Size */
if (type == TYPE_BIN)
len = size - 1 ;
else
len = size ;
tmpL = (len >> 8) & 0xFF ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = len & 0xFF ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the Sub-Ident */
if (type == TYPE_BIN)
tmpL = 0xFF ;
else
tmpL = 0x00 ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteByteSumToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the SumCheck */
tmpL = (ptrFile->sum >> 8) & 0xFF ;
error = WriteByteToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = ptrFile->sum & 0xFF ;
error = WriteByteToB22Tap (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteSyncToTap (70, ptrFile) ;
if (error != ERR_OK) break ;
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
} while (0) ;
return (error);
}
int WriteSaveNameToB19Wav (char* ptrName,
FileInfo* ptrFile)
{
int ii ;
ulong byte ;
ulong tmpL ;
char* ptrDot ;
char tmpS[10] ;
int error ;
do {
/* Upercase the Name */
(void) strupr (ptrName) ;
tmpL = strlen (ptrName) ;
if (tmpL > 7)
tmpL = 7 ;
for ( ii = 0 ; ii < tmpL ; ii++ )
tmpS[ii] = ptrName[ii] ;
tmpS[tmpL] = 0 ;
if (Qcnt == 0) printf ("Save name : %s\n", tmpS) ;
tmpL = 7 - tmpL ;
for ( ii = 0 ; ii < tmpL ; ii++ )
tmpS[ii] = 0 ;
for ( ii = tmpL ; ii < 7 ; ii++ ) {
byte = (ulong) ptrName[6 - ii] ;
if (byte < 0x80)
byte = CodeOld[byte] ;
else
byte = CodeOld[0] ;
tmpS[ii] = (char) ( (byte >> 4) + ((byte << 4) & 0xF0) ) ;
}
tmpS[7] = 0x5F ;
/* Write the Name */
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
for ( ii = 0 ; ii < 8 ; ii++ ) {
error = WriteByteSumToB19Wav (tmpS[ii], ptrFile) ;
if (error != ERR_OK) break ;
}
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
} while (0) ;
return (error);
}
int WriteSaveNameToB16Wav (char* ptrName,
FileInfo* ptrFile)
{
int ii ;
ulong byte ;
ulong tmpL ;
char* ptrDot ;
char tmpS[10] ;
int error ;
do {
/* Search the Dot position */
tmpL = strlen (ptrName) ;
if (tmpL > 7)
tmpL = 7 ;
for ( ii = 0 ; ii < tmpL ; ii++ )
tmpS[ii] = ptrName[ii] ;
tmpS[tmpL] = 0 ;
if (Qcnt == 0) printf ("Save name : %s\n", tmpS) ;
tmpL = 7 - tmpL ;
for ( ii = 0 ; ii < tmpL ; ii++ )
tmpS[ii] = 0 ;
for ( ii = tmpL ; ii < 7 ; ii++ ) {
byte = (ulong) ptrName[6 - ii] ;
if (byte >= 0x80)
byte = 0x20 ;
tmpS[ii] = (char) ( (byte >> 4) + ((byte << 4) & 0xF0) ) ;
}
tmpS[7] = 0x5F ;
/* Write the Name */
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
for ( ii = 0 ; ii < 8 ; ii++ ) {
error = WriteByteSumToB16Wav (tmpS[ii], ptrFile) ;
if (error != ERR_OK) break ;
}
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
} while (0) ;
return (error);
}
int WriteHeadToB19BinWav (ulong addr,
ulong size,
FileInfo* ptrFile)
{
int ii ;
ulong len ;
ulong tmpL ;
int error ;
do {
if (Qcnt == 0)
{
printf ("Start Address: 0x%04X\n", (uint) addr);
printf ("Buffer Length: %d bytes\n", (uint) size);
}
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
error = WriteByteSumToB19Wav (0, ptrFile) ;
if (error != ERR_OK) break ;
}
/* Write the Addresse */
tmpL = ((addr >> 4) & 0xF0) + (addr >> 12) ;
error = WriteByteSumToB19Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = ((addr << 4) & 0xF0) + ((addr >> 4) & 0x0F) ;
error = WriteByteSumToB19Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the Length */
len = size - 1 ;
tmpL = ((len >> 4) & 0xF0) + (len >> 12) ;
error = WriteByteSumToB19Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = ((len << 4) & 0xF0) + ((len >> 4) & 0x0F) ;
error = WriteByteSumToB19Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
} while (0) ;
return (error);
}
int WriteHeadToB16BinWav (ulong addr,
ulong size,
FileInfo* ptrFile)
{
int ii ;
ulong len ;
ulong tmpL ;
int error ;
do {
if (Qcnt == 0)
{
printf ("Start Address: 0x%04X\n", (uint) addr);
printf ("Buffer Length: %d bytes\n", (uint) size);
}
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
for ( ii = 0 ; ii < 4 ; ii++ ) {
error = WriteByteSumToB16Wav (0, ptrFile) ;
if (error != ERR_OK) break ;
}
/* Write the Addresse */
tmpL = ((addr >> 4) & 0xF0) + (addr >> 12) ;
error = WriteByteSumToB16Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = ((addr << 4) & 0xF0) + ((addr >> 4) & 0x0F) ;
error = WriteByteSumToB16Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
/* Write the Length */
len = size - 1 ;
tmpL = ((len >> 4) & 0xF0) + (len >> 12) ;
error = WriteByteSumToB16Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
tmpL = ((len << 4) & 0xF0) + ((len >> 4) & 0x0F) ;
error = WriteByteSumToB16Wav (tmpL, ptrFile) ;
if (error != ERR_OK) break ;
ptrFile->count = 0 ;
ptrFile->sum = 0 ;
} while (0) ;
return (error);
}
int WriteFooterToB22BinTap (ulong type,
FileInfo* ptrFile)
{
ulong sum ;
int error ;
do {
ptrFile->count = 0 ;
if (type != TYPE_BIN) {
error = WriteByteSumToB22Tap (0xFF, ptrFile) ;
if (error != ERR_OK) break ;
}
sum = (ptrFile->sum >> 8) & 0xFF ;
error = WriteByteToB22Tap (sum, ptrFile) ;
if (error != ERR_OK) break ;
sum = ptrFile->sum & 0xFF ;
error = WriteByteToB22Tap (sum, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteSyncToTap (70, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteByteToB22Tap (0x55, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteSyncToTap (70, ptrFile) ;
if (error != ERR_OK) break ;
} while (0) ;
return (error);
}
int WriteFooterToB13BinWav (FileInfo* ptrFile)
{
ulong sum ;
int error ;
do {
ptrFile->count = 0 ;
error = WriteByteSumToB13Wav (0xFF, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteByteToB13Wav (0xFF, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteByteToB13Wav (ptrFile->sum, ptrFile) ;
if (error != ERR_OK) break ;
/* there are 2bits more HIGH at the end of transmission (at least for PC-1402) M. NOSSWITZ */
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
error = WriteBitToWav (1, ptrFile) ;
if (error != ERR_OK) break ;
} while (0) ;
return (error);
}
int ConvertBinToTap (char* ptrSrcFile,
char* ptrDstFile,
ulong type,
ulong pcId,
ulong addr,
ulong nbSync,
char* ptrName)
{
FileInfo info ;
FILE *srcFd ;
int inVal ;
int ii ;
ulong nbByte ;
ulong nbSamp ;
ulong freq ;
ulong sync ;
int error ;
do {
info.ptrFd = NULL ;
info.ident = IDENT_UNKNOWN ;
info.count = 0 ;
info.sum = 0 ;
srcFd = NULL ;
error = ERR_OK ;
/* Open the destination file */
info.ptrFd = fopen (ptrDstFile, "wb") ;
if (info.ptrFd == NULL) {
printf ("%s: Can't open the destination file: %s\n", argP, ptrDstFile) ;
error = ERR_NOK ;
break ;
}
/* Open the source file */
srcFd = fopen (ptrSrcFile, "rb") ;
if (srcFd == NULL) {
printf ("%s: Can't open the source file: %s\n", argP, ptrSrcFile) ;
error = ERR_NOK ;
break ;
}
error = ReadFileLength (&nbByte, &srcFd) ;
if (error != ERR_OK) break ;
if (nbByte > 0x10000) {
printf ("%s: Source file contains more than 65536 bytes\n", argP) ;
error = ERR_NOK ;
break ;
}
if ( (addr + nbByte) > 0x10000) {
printf ("%s: (Address + Size) greater than 65536)\n", argP) ;
error = ERR_NOK ;
break ;
}
if (pcId == 1500)
freq = BASE_FREQ2 ;
else
freq = BASE_FREQ1 ;
sync = (nbSync * freq) / 8 ;
/* Calculate the length and Ident of the destination file */
error = LengthAndIdentOfBinTap (type, pcId, nbByte, sync, &info.ident, &nbSamp) ;
if (error != ERR_OK) break ;
/* Write the header of the destination WAV file */
error = WriteHeadToTap (nbSamp, (freq *2), &info) ;
if (error != ERR_OK) break ;
/* Write the synchro patern for N times */
if (Qcnt == 0) printf ("Synchro size : %d bits\n", sync);
error = WriteSyncToTap (sync, &info) ;
if (error != ERR_OK) break ;
if (Qcnt == 0) {
printf ("Tape format : 0x%02X <- ", (uchar) info.ident) ;
if (type == TYPE_BIN)
printf ("Binary, PC-%d\n", pcId) ;
else
printf ("Basic, PC-%d\n", pcId) ;
}
if (pcId == 1500) {
/* Write the TAP code */
error = WriteIdentToB22Tap (IDENT_PC1500, &info) ;
if (error != ERR_OK) break ;
/* Write the Name */
error = WriteHeadToB22Tap (ptrName, addr, nbByte, type, &info) ;
if (error != ERR_OK) break ;
if ((type == TYPE_BIN) && (Qcnt == 0)) {
printf ("Start Address: 0x%04X\n", (uint) addr);
printf ("Buffer Length: %d bytes\n", (uint) nbByte);
}
}
if ( (info.ident == IDENT_OLD_BAS) ||
(info.ident == IDENT_OLD_BIN) ) {
/* Write the TAP code */
error = WriteByteToB19Wav (info.ident, &info) ;
if (error != ERR_OK) break ;
/* Write the Name */
error = WriteSaveNameToB19Wav (ptrName, &info) ;
if (error != ERR_OK) break ;
}
if ( (info.ident == IDENT_NEW_BAS) ||
(info.ident == IDENT_EXT_BAS) ||
(info.ident == IDENT_NEW_BIN) ) {
/* Write the TAP code */
error = WriteByteToB16Wav (info.ident, &info) ;
if (error != ERR_OK) break ;
/* Write the Name */
error = WriteSaveNameToB16Wav (ptrName, &info) ;
if (error != ERR_OK) break ;
}
switch (info.ident) {
case IDENT_PC15_BAS :
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB22Tap (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteFooterToB22BinTap (type, &info) ;
break ;
case IDENT_PC15_BIN :
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB22Tap (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteFooterToB22BinTap (type, &info) ;
break ;
case IDENT_OLD_BAS :
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB19Wav (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteByteToB19Wav (0xF0, &info) ;
break ;
case IDENT_OLD_BIN :
/* Write the addresse and length */
error = WriteHeadToB19BinWav (addr, nbByte, &info) ;
if (error != ERR_OK) break ;
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB19Wav (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteByteToB19Wav (0xF0, &info) ;
break ;
case IDENT_NEW_BAS :
case IDENT_EXT_BAS :
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB13Wav (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteFooterToB13BinWav (&info) ;
break ;
case IDENT_NEW_BIN :
/* Write the addresse and length */
error = WriteHeadToB16BinWav (addr, nbByte, &info) ;
if (error != ERR_OK) break ;
/* Write the datas */
do {
inVal = fgetc (srcFd) ;
if (inVal == EOF) break ;
error = WriteByteSumToB13Wav (inVal, &info) ;
if (error != ERR_OK) break ;
} while (1) ;
if (error != ERR_OK) break ;
/* Write the END code */
error = WriteFooterToB13BinWav (&info) ;
break ;
default :
printf ("%s: Unknown Ident\n", argP) ;
break ;
}
} while (0) ;
/* Close the source file */
if (srcFd != NULL) {
error = fclose (srcFd) ;
if (error != ERR_OK) {
printf ("%s: Can't close the source file\n", argP) ;
}
}
/* Close the destination file */
if (info.ptrFd != NULL) {
error = fclose (info.ptrFd) ;
if (error != ERR_OK) {
printf ("%s: Can't close the destination file\n", argP) ;
}
}
return (error);
}
void PrintHelp (void) /* 1 2 3 4 5 6 7 8 */
{ /* 12345678901234567890123456789012345678901234567890123456789012345678901234567890 */
printf ("Usage: %s [Options] SrcFile [DstFile]\n", argP) ;
printf ("SrcFile : Binary image file (usualy produced by 'BAS2IMG' or 'WAV2BIN')\n") ;
printf ("Options:\n") ;
printf ("DstFile : WAV file (default: SrcFile.wav)\n") ;
printf ("-t, --type=TYPE : Source file type\n") ;
printf (" bin Binary image file (Assembly program or Datas)\n") ;
printf (" img Binary image file (BASIC-program, default: img)\n") ;
// printf ("-p, --pc=NUMBER : Sharp pocket computer, currently available\n") ;
// printf (" 1245, 1251, 1261, 1350, 1360, 1401, 1402,\n") ;
// printf (" 1403, 1450, 1475, 1500 (default: 1500)\n") ;
printf ("-p, --pc=NUMBER : Sharp pocket computer, currently available\n") ;
printf (" 1245, 1251, 1261, 1500 (default: 1500)\n") ;
printf ("-a, --addr=VALUE : Start addresse, needed for BIN type\n") ;
printf (" 0 to 65535, or 0x0000 to 0xFFFF (default: 0)\n") ;
printf ("-s, --sync=VALUE : Synchronisation duration, expressed in seconds\n") ;
printf (" 1 to 8 (default: 2)\n") ;
printf ("-n, --name=NAME : Sharp file name (7 characters max, 16 for the PC-1500)\n") ;
printf (" (default: DstFile without extension, nor path)\n") ;
printf ("-q, --quiet : Quiet mode (No display output)\n") ;
printf (" --help : Display this information\n") ;
printf (" --version : Display version information\n") ;
exit( 1 ); /* no arguments were passed */
}
void PrintVersion (void)
{ char argPU[cLPF] = "" ;
strcpy(argPU, argP) ;
printf ("%s (%s) version: 1.4\n", strupr(argPU) ) ;
printf ("Author: Pocket -> www.pocketmuseum.com\n") ; /* Please do not remove */
printf (" Modified for TAP format by O2S\n") ; /* Please do not remove */
printf ("This is free software. There is NO warranty;\n") ;
printf ("not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n") ;
exit( 1 ); /* no arguments were passed */
}
void MoreInfo (void)
{ printf("%s: '%s --help' gives you more information\n", argP, argP);
exit( 1 ); /* no arguments were passed */
}
int main ( int argc, char **argv ) /* (int argc, char* argv[]) */
{ /* 0=SrcFile 1=[DstFile] 2=[-t] 3=[-p] 4=[-a] 5=[-s] 6=[-n] */
char argD[7][cLPF] = { "", "", "img", "1500", "0x0000", "2", "" } ;
char argS[cLPF] = "", *ptrToken, *ptrErr, tmp ;
uint FILEcnt = 0, Tcnt = 0, PCcnt = 0, Acnt = 0, Scnt = 0, Ncnt = 0 ;
ulong type, pcId, sync, addr ;
int option_index, error, c ;
static int longval ;
struct option long_options[] =
{
{"type", required_argument, 0, 't'},
{"pc", required_argument, 0, 'p'},
{"addr", required_argument, 0, 'a'},
{"sync", required_argument, 0, 's'},
{"name", optional_argument, 0, 'n'},
{"quiet", no_argument, 0, 'q'},
{"version", no_argument, &longval, 'v'}, /* long option only */
{"help", no_argument, &longval, 'h'}, /* long option only */
{0, 0, 0, 0}
};
/* ProgramName */
if (strrchr (argv[0], '\\')) strcpy(argP, 1 + strrchr (argv[0], '\\')); /* Windows path separator '\' */
else if (strrchr (argv[0], '/')) strcpy(argP, 1 + strrchr (argv[0], '/')); /* Linux path separator '/' */
else strcpy(argP, argv[0]);
if ( strrchr (argP, '.')) *(strrchr (argP, '.')) = '\0'; /* Extension separator '.' */
do
{
while (1) {
error = ERR_OK ;
addr = 0 ;
/* getopt_long stores the option index here. */
option_index = 0;
c = getopt_long (argc, argv, "t:p:a:s:n:qvh", long_options, &option_index);
/* Detect the end of the options. */
if (c == -1) break;
switch (c)
{
case 't': strcpy( argD[2], optarg); Tcnt++; break;
case 'p': strcpy( argD[3], optarg); PCcnt++; break;
case 'a': strcpy( argD[4], optarg); Acnt++; break;
case 's': strcpy( argD[5], optarg); Scnt++; break;
case 'n': { if ( optarg != 0 ) strcpy( argD[6], optarg);
Ncnt++; break; }
case 'q': Qcnt++; break;
case 0:
switch (longval) {
case 'v': PrintVersion (); break;
case 'h': PrintHelp (); break;
} break;
default : MoreInfo (); break;
}
}
if (optind < argc) /* get non-option ARGV-elements */
{
while (optind < argc) {
strcpy(argD[FILEcnt!=0], argv[optind++]);
FILEcnt++;
}
}
if (FILEcnt < 1) { printf("%s: Missing Operand after '%s'\n", argP, argP); MoreInfo (); }
if ((FILEcnt > 2) || (Tcnt > 1) || (PCcnt > 1) || (Acnt > 1) || (Scnt > 1) ||
(Ncnt > 1) || (Qcnt > 1)) { printf("%s: Operand error in '%s'\n", argP, argP); MoreInfo (); }
if (FILEcnt == 1)
{
if ( strrchr (argD[0], '.')) strncat (argD[1], argD[0], strrchr (argD[0], '.') - argD[0] ); /* GetSrcFile */
strcat (argD[1], ".wav" ); /* DstFile=SrcFile.wav */
}
(void) strupr (argD[2]) ;
type = TYPE_NOK ;
if (strcmp (argD[2], "BIN") == 0)
type = TYPE_BIN ;
if (strcmp (argD[2], "IMG") == 0)
type = TYPE_IMG ;
if (type == TYPE_NOK) {
printf ("%s: Source file type %s is not valid\n", argP, argD[2]) ;
MoreInfo ();
break ;
}
/* Compare the PC Ident to the allowed tokens */
if (strlen (argD[3]) == 0) {
printf ("%s: No pocket computer specified\n", argP) ;
MoreInfo ();
break ;
}
pcId = (ulong) strtol (argD[3], &ptrErr, 0) ;
if (pcId == 0) {
printf ("%s: Pocket computer %s is not valid\n", argP, argD[3]) ;
MoreInfo ();
break ;
}
switch (pcId) {
case 1500 :
case 1245 :
case 1251 :
case 1261 :
break ;
case 1350 :
case 1360 :
case 1401 :
case 1402 :
case 1403 :
case 1450 :
case 1475 :
default :
printf ("%s: Pocket computer %s not implemented\n", argP, argD[3]) ;
MoreInfo ();
error = ERR_NOK ;
break ;
}
if (error != ERR_OK) break ;
/* Convert the Address in a ulong if necessary */
if (type == TYPE_BIN) {
addr = (ulong) strtol (argD[4], &ptrErr, 0) ;
if (*ptrErr != 0) { /* was (*ptrErr != NULL) */
tmp = *ptrErr ;
*ptrErr = 0 ;
printf ("%s: Start address is not valid '%s -> ", argP, argD[4]) ;
*ptrErr = tmp ;
printf ("%s'\n", ptrErr) ;
MoreInfo ();
break ;
}
if ( (addr < 0) ||
(addr > 0xFFFF) ) {
printf ("%s: Start address '%s' is out of range\n", argP, argD[4]) ;
MoreInfo ();
break ;
}
}
/* Convert the Sync length in a ulong */
sync = (ulong) strtol (argD[5], &ptrErr, 0) ;
if (*ptrErr != 0) { /* was (*ptrErr != NULL) */
tmp = *ptrErr ;
*ptrErr = 0 ;
printf ("%s: Sync length is not valid '%s -> ", argP, argD[5]) ;
*ptrErr = tmp ;
printf ("%s'\n", ptrErr) ;
MoreInfo ();
break ;
}
if ( (sync < 1) ||
(sync > 10) ) {
printf ("%s: Sync length '%s' is out of range\n", argP, argD[5]) ;
MoreInfo ();
break ;
}
/* Check if the name-option is used and no name is defined */
if ( ( Ncnt == 1 ) && ( strlen (argD[6]) == 0 ) ) {
/* Search the last colon position */
ptrToken = strrchr (argD[1], CHAR_COLON) ;
if (ptrToken == NULL)
(void) strcpy (argS, argD[1]) ;
else
(void) strcpy (argS, ptrToken + 1) ;
/* Search the last slash position */
ptrToken = strrchr (argS, CHAR_SLASH) ;
if (ptrToken == NULL)
(void) strcpy (argD[6], argS) ;
else
(void) strcpy (argD[6], ptrToken + 1) ;
/* Search the dot position */
ptrToken = strchr (argD[6], CHAR_DOT) ;
if (ptrToken != NULL)
*ptrToken = 0 ;
}
/* Replace the underscore with space in the name */
ptrToken = strchr (argD[6], CHAR_UNDERSCORE) ;
while (ptrToken != NULL) {
*ptrToken = CHAR_SPACE ;
ptrToken = strchr (argD[6], CHAR_UNDERSCORE) ;
}
/* Call the Convert function */
(void) ConvertBinToTap (argD[0], argD[1], type, pcId, addr, sync, argD[6]) ;
} while (0) ;
}