#include <string.h>
/* common */
+#include "chartype.h"
#include "check.h"
#include "cmdline.h"
#include "version.h"
/* sp65 */
#include "attr.h"
-#include "bin.h"
+#include "asm.h"
#include "error.h"
-void WriteAsmFile (const StrBuf* Data, const Collection* A)
-/* Write the contents of Data to the given file in assembler (ca65) format */
+static int ValidIdentifier (const char* L)
+/* Check an assembler label for validity */
{
- FILE* F;
- const char* D;
- unsigned Size;
- unsigned Base = 16;
- unsigned BytesPerLine = 16;
- char C;
+ /* Must begin with underscore or alphabetic character */
+ if (*L != '_' && !IsAlpha (*L)) {
+ return 0;
+ }
+ ++L;
+ /* Remainder must be as above plus digits */
+ while (*L) {
+ if (*L != '_' && !IsAlNum (*L)) {
+ return 0;
+ }
+ ++L;
+ }
+
+ /* Ok */
+ return 1;
+}
- /* Get the file name */
- const char* Name = NeedAttrVal (A, "name", "write");
+
+
+static unsigned GetBytesPerLine (const Collection* A)
+/* Return the number of bytes per line from the attribute collection A */
+{
+ char C;
+ unsigned BytesPerLine = 16;
/* Check for a bytesperline attribute */
const char* V = GetAttrVal (A, "bytesperline");
(BytesPerLine < 1 || BytesPerLine > 64)) {
Error ("Invalid value for attribute `bytesperline'");
}
+ return BytesPerLine;
+}
+
+
+
+static unsigned GetBase (const Collection* A)
+/* Return the number base from the attribute collection A */
+{
+ char C;
+ unsigned Base = 16;
/* Check for a base attribute */
- V = GetAttrVal (A, "base");
+ const char* V = GetAttrVal (A, "base");
if ((V && sscanf (V, "%u%c", &Base, &C) != 1) ||
(Base != 2 && Base != 10 && Base != 16)) {
Error ("Invalid value for attribute `base'");
}
+ return Base;
+}
+
+
+
+static const char* GetIdentifier (const Collection* A)
+/* Return the label identifier from the attribute collection A */
+{
+ /* Check for a ident attribute */
+ const char* Ident = GetAttrVal (A, "ident");
+ if (Ident && !ValidIdentifier (Ident)) {
+ Error ("Invalid value for attribute `ident'");
+ }
+ return Ident;
+}
+
+
+
+void WriteAsmFile (const StrBuf* Data, const Collection* A, const Bitmap* B)
+/* Write the contents of Data to the given file in assembler (ca65) format */
+{
+ FILE* F;
+ const char* D;
+ unsigned Size;
+
+
+ /* Get the name of the image */
+ const StrBuf* S = GetBitmapName (B);
+
+ /* Get the file name */
+ const char* Name = NeedAttrVal (A, "name", "write");
+
+ /* Check the number of bytes per line */
+ unsigned BytesPerLine = GetBytesPerLine (A);
+
+ /* Get the number base */
+ unsigned Base = GetBase (A);
+
+ /* Get the identifier */
+ const char* Ident = GetIdentifier (A);
/* Open the output file */
F = fopen (Name, "w");
/* Write a readable header */
fprintf (F,
";\n"
- "; This file was generated by %s %s\n"
+ "; This file was generated by %s %s from\n"
+ "; %.*s (%ux%u, %u colors%s)\n"
";\n"
"\n",
ProgName,
- GetVersionAsString ());
+ GetVersionAsString (),
+ SB_GetLen (S), SB_GetConstBuf (S),
+ GetBitmapWidth (B), GetBitmapHeight (B),
+ GetBitmapColors (B),
+ BitmapIsIndexed (B)? ", indexed" : "");
+
+ /* If we have an assembler label, output that */
+ if (Ident) {
+ fprintf (F,
+ ".proc %s\n"
+ " COLORS = %u\n"
+ " WIDTH = %u\n"
+ " HEIGHT = %u\n",
+ Ident,
+ GetBitmapColors (B),
+ GetBitmapWidth (B),
+ GetBitmapHeight (B));
+ }
/* Write the data */
D = SB_GetConstBuf (Data);
Size -= Chunk;
}
+ /* Terminate the .proc if we had an identifier */
+ if (Ident) {
+ fputs (".endproc\n", F);
+ }
+
/* Add an empty line at the end */
fputc ('\n', F);
Error ("Error closing output file `%s': %s", Name, strerror (errno));
}
}
-
-
-