Mercurial > hg > dmlib
comparison lib64gfx.c @ 510:43ea59887c69
Start work on making C64 formats encoding possible by changing DMDecodeOps
to DMEncDecOps and adding fields and op enums for custom encode functions, renaming,
etc. Split generic op sanity checking into a separate function in
preparation for its use in generic encoding function.
author | Matti Hamalainen <ccr@tnsp.org> |
---|---|
date | Mon, 19 Nov 2012 15:06:01 +0200 |
parents | 1ed5025c2538 |
children | 4cdcaeb68b54 |
comparison
equal
deleted
inserted
replaced
509:e8e244036ee4 | 510:43ea59887c69 |
---|---|
195 | 195 |
196 return DM_PROBE_SCORE_FALSE; | 196 return DM_PROBE_SCORE_FALSE; |
197 } | 197 } |
198 | 198 |
199 | 199 |
200 static BOOL fmtDrazLaceSetLaceType(DMC64Image *img, const struct _DMDecodeOp *op, const Uint8 *buf, const size_t len) | 200 static BOOL fmtDrazLaceSetLaceType(DMC64Image *img, const struct _DMC64EncDecOp *op, const Uint8 *buf, const size_t len) |
201 { | 201 { |
202 (void) len; | 202 (void) len; |
203 | 203 |
204 img->laceType = buf[op->offs] ? DM_C64ILACE_RES : DM_C64ILACE_COLOR; | 204 img->laceType = buf[op->offs] ? DM_C64ILACE_RES : DM_C64ILACE_COLOR; |
205 img->laceBank2 = 0; | 205 img->laceBank2 = 0; |
280 return DM_PROBE_SCORE_GOOD; | 280 return DM_PROBE_SCORE_GOOD; |
281 return DM_PROBE_SCORE_FALSE; | 281 return DM_PROBE_SCORE_FALSE; |
282 } | 282 } |
283 | 283 |
284 | 284 |
285 static BOOL fmtTruePaintSetLaceType(DMC64Image *img, const struct _DMDecodeOp *op, const Uint8 *buf, const size_t len) | 285 static BOOL fmtTruePaintSetLaceType(DMC64Image *img, const struct _DMC64EncDecOp *op, const Uint8 *buf, const size_t len) |
286 { | 286 { |
287 (void) op; | 287 (void) op; |
288 (void) buf; | 288 (void) buf; |
289 (void) len; | 289 (void) len; |
290 img->laceType = DM_C64ILACE_RES; | 290 img->laceType = DM_C64ILACE_RES; |
299 DM_C64IFMT_MC, ".drp", "DrazPaint 2.0 (packed)", | 299 DM_C64IFMT_MC, ".drp", "DrazPaint 2.0 (packed)", |
300 fmtProbeDrazPaint20Packed, fmtDecodeDrazPaintPacked, | 300 fmtProbeDrazPaint20Packed, fmtDecodeDrazPaintPacked, |
301 NULL, NULL, NULL, | 301 NULL, NULL, NULL, |
302 4, | 302 4, |
303 { | 303 { |
304 { DT_COLOR_RAM, 0x0000, 0, 0, NULL }, | 304 { DT_COLOR_RAM, 0x0000, 0, 0, NULL, NULL }, |
305 { DT_BITMAP, 0x0800, 0, 0, NULL }, | 305 { DT_BITMAP, 0x0800, 0, 0, NULL, NULL }, |
306 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL }, | 306 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL, NULL }, |
307 { DT_BGCOLOR, 0x2740, 0, 0, NULL }, | 307 { DT_BGCOLOR, 0x2740, 0, 0, NULL, NULL }, |
308 } | 308 } |
309 }, | 309 }, |
310 | 310 |
311 { | 311 { |
312 DM_C64IFMT_MC_ILACE, ".dlp", "DrazLace 1.0 (packed)", | 312 DM_C64IFMT_MC_ILACE, ".dlp", "DrazLace 1.0 (packed)", |
313 fmtProbeDrazLace10Packed, fmtDecodeDrazPaintPacked, | 313 fmtProbeDrazLace10Packed, fmtDecodeDrazPaintPacked, |
314 NULL, NULL, NULL, | 314 NULL, NULL, NULL, |
315 6, | 315 6, |
316 { | 316 { |
317 { DT_COLOR_RAM, 0x0000, 0, 0, NULL }, | 317 { DT_COLOR_RAM, 0x0000, 0, 0, NULL, NULL }, |
318 { DT_BITMAP, 0x0800, 0, 0, NULL }, | 318 { DT_BITMAP, 0x0800, 0, 0, NULL, NULL }, |
319 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL }, | 319 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL, NULL }, |
320 { DT_BGCOLOR, 0x2740, 0, 0, NULL }, | 320 { DT_BGCOLOR, 0x2740, 0, 0, NULL, NULL }, |
321 { DT_BITMAP, 0x2800, 1, 0, NULL }, | 321 { DT_BITMAP, 0x2800, 1, 0, NULL, NULL }, |
322 { DT_FUNCTION, 0x2742, 0, 1, fmtDrazLaceSetLaceType }, | 322 { DT_DEC_FUNCTION, 0x2742, 0, 1, fmtDrazLaceSetLaceType, NULL }, |
323 } | 323 } |
324 }, | 324 }, |
325 | 325 |
326 { | 326 { |
327 DM_C64IFMT_MC, ".drp", "DrazPaint (unpacked)", | 327 DM_C64IFMT_MC, ".drp", "DrazPaint (unpacked)", |
328 fmtProbeDrazPaint, NULL, | 328 fmtProbeDrazPaint, NULL, |
329 NULL, NULL, NULL, | 329 NULL, NULL, NULL, |
330 4, | 330 4, |
331 { | 331 { |
332 { DT_COLOR_RAM, 0x0000, 0, 0, NULL }, | 332 { DT_COLOR_RAM, 0x0000, 0, 0, NULL, NULL }, |
333 { DT_BITMAP, 0x0800, 0, 0, NULL }, | 333 { DT_BITMAP, 0x0800, 0, 0, NULL, NULL }, |
334 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL }, | 334 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL, NULL }, |
335 { DT_BGCOLOR, 0x2740, 0, 0, NULL }, | 335 { DT_BGCOLOR, 0x2740, 0, 0, NULL, NULL }, |
336 } | 336 } |
337 }, | 337 }, |
338 | 338 |
339 { | 339 { |
340 DM_C64IFMT_MC_ILACE, ".drl", "DrazLace 1.0 (unpacked)", | 340 DM_C64IFMT_MC_ILACE, ".drl", "DrazLace 1.0 (unpacked)", |
341 fmtProbeDrazLace10, NULL, | 341 fmtProbeDrazLace10, NULL, |
342 NULL, NULL, NULL, | 342 NULL, NULL, NULL, |
343 6, | 343 6, |
344 { | 344 { |
345 { DT_COLOR_RAM, 0x0000, 0, 0, NULL }, | 345 { DT_COLOR_RAM, 0x0000, 0, 0, NULL, NULL }, |
346 { DT_BITMAP, 0x0800, 0, 0, NULL }, | 346 { DT_BITMAP, 0x0800, 0, 0, NULL, NULL }, |
347 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL }, | 347 { DT_SCREEN_RAM, 0x0400, 0, 0, NULL, NULL }, |
348 { DT_BGCOLOR, 0x2740, 0, 0, NULL }, | 348 { DT_BGCOLOR, 0x2740, 0, 0, NULL, NULL }, |
349 { DT_BITMAP, 0x2800, 1, 0, NULL }, | 349 { DT_BITMAP, 0x2800, 1, 0, NULL, NULL }, |
350 { DT_FUNCTION, 0x2742, 0, 1, fmtDrazLaceSetLaceType }, | 350 { DT_DEC_FUNCTION, 0x2742, 0, 1, fmtDrazLaceSetLaceType, NULL }, |
351 } | 351 } |
352 }, | 352 }, |
353 | 353 |
354 { | 354 { |
355 DM_C64IFMT_MC_ILACE, ".mci", "Truepaint (unpacked)", | 355 DM_C64IFMT_MC_ILACE, ".mci", "Truepaint (unpacked)", |
356 fmtProbeTruePaint, NULL, | 356 fmtProbeTruePaint, NULL, |
357 NULL, NULL, NULL, | 357 NULL, NULL, NULL, |
358 6, | 358 6, |
359 { | 359 { |
360 { DT_SCREEN_RAM, 0x0000, 0, 0, NULL }, | 360 { DT_SCREEN_RAM, 0x0000, 0, 0, NULL, NULL }, |
361 { DT_BGCOLOR, 0x03e8, 0, 0, NULL }, | 361 { DT_BGCOLOR, 0x03e8, 0, 0, NULL, NULL }, |
362 { DT_BITMAP, 0x0400, 0, 0, NULL }, | 362 { DT_BITMAP, 0x0400, 0, 0, NULL, NULL }, |
363 { DT_BITMAP, 0x2400, 1, 0, NULL }, | 363 { DT_BITMAP, 0x2400, 1, 0, NULL, NULL }, |
364 { DT_SCREEN_RAM, 0x4400, 1, 0, NULL }, | 364 { DT_SCREEN_RAM, 0x4400, 1, 0, NULL, NULL }, |
365 { DT_COLOR_RAM, 0x4800, 0, 0, NULL }, | 365 { DT_COLOR_RAM, 0x4800, 0, 0, NULL, NULL }, |
366 { DT_FUNCTION, 0x0000, 0, 0, fmtTruePaintSetLaceType }, | 366 { DT_DEC_FUNCTION, 0x0000, 0, 0, fmtTruePaintSetLaceType, NULL }, |
367 } | 367 } |
368 }, | 368 }, |
369 | 369 |
370 { | 370 { |
371 DM_C64IFMT_MC, ".kla", "Koala Paint (unpacked)", | 371 DM_C64IFMT_MC, ".kla", "Koala Paint (unpacked)", |
372 fmtProbeKoalaPaint, NULL, | 372 fmtProbeKoalaPaint, NULL, |
373 NULL, NULL, NULL, | 373 NULL, NULL, NULL, |
374 4, | 374 4, |
375 { | 375 { |
376 { DT_COLOR_RAM, 0x2328, 0, 0, NULL }, | 376 { DT_COLOR_RAM, 0x2328, 0, 0, NULL, NULL }, |
377 { DT_BITMAP, 0x0000, 0, 0, NULL }, | 377 { DT_BITMAP, 0x0000, 0, 0, NULL, NULL }, |
378 { DT_SCREEN_RAM, 0x1f40, 0, 0, NULL }, | 378 { DT_SCREEN_RAM, 0x1f40, 0, 0, NULL, NULL }, |
379 { DT_BGCOLOR, 0x2710, 0, 0, NULL }, | 379 { DT_BGCOLOR, 0x2710, 0, 0, NULL, NULL }, |
380 } | 380 } |
381 }, | 381 }, |
382 | 382 |
383 { | 383 { |
384 DM_C64IFMT_MC, ".ami", "Amica Paint (packed)", | 384 DM_C64IFMT_MC, ".ami", "Amica Paint (packed)", |
385 fmtProbeAmicaPaintPacked, fmtDecodeAmicaPaintPacked, | 385 fmtProbeAmicaPaintPacked, fmtDecodeAmicaPaintPacked, |
386 NULL, NULL, NULL, | 386 NULL, NULL, NULL, |
387 4, | 387 4, |
388 { | 388 { |
389 { DT_COLOR_RAM, 0x2328, 0, 0, NULL }, | 389 { DT_COLOR_RAM, 0x2328, 0, 0, NULL, NULL }, |
390 { DT_BITMAP, 0x0000, 0, 0, NULL }, | 390 { DT_BITMAP, 0x0000, 0, 0, NULL, NULL }, |
391 { DT_SCREEN_RAM, 0x1f40, 0, 0, NULL }, | 391 { DT_SCREEN_RAM, 0x1f40, 0, 0, NULL, NULL }, |
392 { DT_BGCOLOR, 0x2710, 0, 0, NULL }, | 392 { DT_BGCOLOR, 0x2710, 0, 0, NULL, NULL }, |
393 } | 393 } |
394 }, | 394 }, |
395 | 395 |
396 }; | 396 }; |
397 | 397 |
421 else | 421 else |
422 return DM_PROBE_SCORE_FALSE; | 422 return DM_PROBE_SCORE_FALSE; |
423 } | 423 } |
424 | 424 |
425 | 425 |
426 static int dmC64SanityCheckEncDecOp(const int i, const DMC64EncDecOp *op) | |
427 { | |
428 if (op->bank < 0 || op->bank >= C64_SCR_MAX_BANK) | |
429 { | |
430 dmError("Invalid bank %d definition in generic encode/decode operator %d @ #%d.\n", | |
431 op->bank, op->type, i); | |
432 return DMERR_INTERNAL; | |
433 } | |
434 | |
435 if (op->type < 0 || op->type >= DT_LAST) | |
436 { | |
437 dmError("Invalid encode/decode operator type %d @ #%d.\n", | |
438 op->type, i); | |
439 return DMERR_INTERNAL; | |
440 } | |
441 | |
442 return DMERR_OK; | |
443 } | |
444 | |
445 | |
426 int dmC64DecodeGenericBMP(DMC64Image *img, const Uint8 *buf, | 446 int dmC64DecodeGenericBMP(DMC64Image *img, const Uint8 *buf, |
427 const size_t len, const DMC64ImageFormat *fmt) | 447 const size_t len, const DMC64ImageFormat *fmt) |
428 { | 448 { |
429 int i; | 449 int i; |
430 | 450 |
431 memset(img, 0, sizeof(*img)); | 451 memset(img, 0, sizeof(*img)); |
432 img->type = fmt->type; | 452 img->type = fmt->type; |
433 | 453 |
434 for (i = 0; i < fmt->ndecodeOps; i++) | 454 for (i = 0; i < fmt->ndecencOps; i++) |
435 { | 455 { |
436 const DMDecodeOp *op = &fmt->decodeOps[i]; | 456 const DMC64EncDecOp *op = &fmt->decencOps[i]; |
437 const Uint8 *src; | 457 const Uint8 *src; |
438 size_t size; | 458 size_t size; |
439 | 459 int res; |
440 if (op->bank < 0 || op->bank >= C64_SCR_MAX_BANK) | 460 |
441 { | 461 if ((res = dmC64SanityCheckEncDecOp(i, op)) != DMERR_OK) |
442 dmError("Invalid bank %d definition in generic decode operator %d @ #%d.\n", | 462 return res; |
443 op->bank, op->type, i); | |
444 return DMERR_INTERNAL; | |
445 } | |
446 | |
447 if (op->type < 0 || op->type >= DT_LAST) | |
448 { | |
449 dmError("Invalid decode operator type %d @ #%d.\n", | |
450 op->type, i); | |
451 return DMERR_INTERNAL; | |
452 } | |
453 | 463 |
454 size = (op->size == 0) ? dmC64DefaultSizes[op->type] : op->size; | 464 size = (op->size == 0) ? dmC64DefaultSizes[op->type] : op->size; |
455 | 465 |
456 if (op->offs + size > len) | 466 if (op->offs + size > len) |
457 { | 467 { |
458 dmError("Decode out of bounds, op #%d type=%d, offs=%d ($%04x), bank=%d, size=%d ($%04x) @ %d ($%04x\n", | 468 dmError("Decode out of bounds, op #%d type=%d, offs=%d ($%04x), " |
469 "bank=%d, size=%d ($%04x) @ %d ($%04x)\n", | |
459 i, op->type, op->offs, op->offs, op->bank, size, size, len, len); | 470 i, op->type, op->offs, op->offs, op->bank, size, size, len, len); |
460 return DMERR_INVALID_DATA; | 471 return DMERR_INVALID_DATA; |
461 } | 472 } |
462 | 473 |
463 src = buf + op->offs; | 474 src = buf + op->offs; |
467 case DT_COLOR_RAM: memcpy(img->color[op->bank], src, size); break; | 478 case DT_COLOR_RAM: memcpy(img->color[op->bank], src, size); break; |
468 case DT_BITMAP: memcpy(img->bitmap[op->bank], src, size); break; | 479 case DT_BITMAP: memcpy(img->bitmap[op->bank], src, size); break; |
469 case DT_SCREEN_RAM: memcpy(img->screen[op->bank], src, size); break; | 480 case DT_SCREEN_RAM: memcpy(img->screen[op->bank], src, size); break; |
470 case DT_BGCOLOR: img->bgcolor = *src; break; | 481 case DT_BGCOLOR: img->bgcolor = *src; break; |
471 case DT_EXTRADATA: memcpy(img->extradata, src, size); break; | 482 case DT_EXTRADATA: memcpy(img->extradata, src, size); break; |
472 case DT_FUNCTION: | 483 case DT_DEC_FUNCTION: |
473 if (op->function == NULL) | 484 if (op->decfunction == NULL) |
474 { | 485 { |
475 dmError("Decode op is a function, but function ptr is NULL: op #%d, offs=%d ($%04x), bank=%d, size=%d ($%04x) @ %d ($%04x\n", | 486 dmError("Decode op is a function, but function ptr is NULL: " |
487 "op #%d, offs=%d ($%04x), bank=%d, size=%d ($%04x) @ %d ($%04x)\n", | |
476 i, op->offs, op->offs, op->bank, size, size, len, len); | 488 i, op->offs, op->offs, op->bank, size, size, len, len); |
477 return DMERR_INTERNAL; | 489 return DMERR_INTERNAL; |
478 } | 490 } |
479 if (!op->function(img, op, buf, len)) | 491 if (!op->decfunction(img, op, buf, len)) |
480 { | 492 { |
481 dmError("Decode op custom function failed: op #%d, offs=%d ($%04x), bank=%d, size=%d ($%04x) @ %d ($%04x\n", | 493 dmError("Decode op custom function failed: op #%d, " |
494 "offs=%d ($%04x), bank=%d, size=%d ($%04x) @ %d ($%04x)\n", | |
482 i, op->offs, op->offs, op->bank, size, size, len, len); | 495 i, op->offs, op->offs, op->bank, size, size, len, len); |
483 return DMERR_INTERNAL; | 496 return DMERR_INTERNAL; |
484 } | 497 } |
485 break; | 498 break; |
486 } | 499 } |