Mercurial > hg > dmlib
diff jssmod.c @ 0:32250b436bca
Initial re-import.
author | Matti Hamalainen <ccr@tnsp.org> |
---|---|
date | Fri, 28 Sep 2012 01:54:23 +0300 |
parents | |
children | 048536ad01e0 |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/jssmod.c Fri Sep 28 01:54:23 2012 +0300 @@ -0,0 +1,380 @@ +/* + * miniJSS - Module structure and handling routines + * Programmed and designed by Matti 'ccr' Hamalainen + * (C) Copyright 2006-2007 Tecnic Software productions (TNSP) + */ +#include "jssmod.h" +#include <string.h> + + +#ifndef JSS_LIGHT +/* Take given data until maxlen reached, make a string + */ +char *jssASCIItoStr(char * sdata, const char endByte, const size_t maxLen) +{ + size_t i, k; + char *res; + + for (i = 0; sdata[i] && i < maxLen; i++); + + res = (char *) dmMalloc(i + 1); + if (res == NULL) + return NULL; + + for (k = 0; sdata[k] != endByte && k < i; k++) + res[k] = sdata[k]; + + res[k] = 0; + + return res; +} + + +/* Encodes a given 8-bit sample + */ +BOOL jssEncodeSample8(Uint8 * sdata, const size_t srcSize, const int ops) +{ + size_t ssize = srcSize; + Sint8 t, value = 0; + + while (ssize--) + { + t = *sdata; + + if (ops & jsampFlipSign) + t ^= 0x80; + + if (ops & jsampDelta) + { + int n = t - value; + value = t; + t = n; + } + + *(sdata++) = t; + } + + return TRUE; +} + + +/* Decodes a given 16-bit sample + */ +BOOL jssEncodeSample16(Uint16 * srcData, const size_t srcSize, const int ops) +{ + // "Split" the 16-bit samples into 8-bit halves + if (ops & jsampSplit) + { + // Allocate temporary processing buffer + size_t ssize, bufSize = srcSize * sizeof(Sint16); + Uint8 *bp1, *bp2; + Sint16 t, *sdata, *tmpBuf = dmMalloc(bufSize); + if (tmpBuf == NULL) return FALSE; + + sdata = tmpBuf; + bp1 = (Uint8 *) srcData; + bp2 = bp1 + srcSize; + ssize = srcSize; + + while (ssize--) + { + t = (*sdata++); + *bp1++ = t >> 8; + *bp2++ = t & 0xff; + } + + memcpy(srcData, tmpBuf, bufSize); + dmFree(tmpBuf); + + return jssEncodeSample8((Uint8 *) srcData, bufSize, ops); + } + else + { + Sint16 t, p, value = 0, *sdata = (Sint16 *) srcData; + size_t ssize = srcSize; + + while (ssize--) + { + if (ops & jsampSwapEndianess) + { + p = *sdata; + t = ((p >> 8) & 0xff) | ((p & 0xff) << 8); + } else + t = *sdata; + + if (ops & jsampDelta) + { + int n = t - value; + value = t; + t = n; + } + + if (ops & jsampFlipSign) + t ^= 0x8000; + + *(sdata++) = t; + } + } + return TRUE; +} +#endif + + +/* Decodes a given 8-bit sample + */ +BOOL jssDecodeSample8(Uint8 * sdata, const size_t srcSize, const int ops) +{ + size_t ssize = srcSize; + Sint8 t, value = 0; + + while (ssize--) + { + t = *sdata; + + if (ops & jsampDelta) + t = value = t + value; + + if (ops & jsampFlipSign) + t ^= 0x80; + + *(sdata++) = t; + } + return TRUE; +} + + +/* Decodes a given 16-bit sample + */ +BOOL jssDecodeSample16(Uint16 * srcData, const size_t srcSize, const int ops) +{ + if (ops & jsampSplit) + { + size_t ssize, bufSize = srcSize * sizeof(Uint16); + Uint8 *bp1, *bp2; + Sint16 *tmpBuf, *sdata; + + if (!jssDecodeSample8((Uint8 *) srcData, bufSize, ops)) + return FALSE; + + tmpBuf = dmMalloc(bufSize); + if (tmpBuf == NULL) return FALSE; + memcpy(tmpBuf, srcData, bufSize); + + sdata = (Sint16 *) srcData; + bp1 = (Uint8 *) tmpBuf; + bp2 = bp1 + srcSize; + ssize = srcSize; + while (ssize--) + { + *sdata++ = (*bp1++ << 8) | (*bp2++ & 0xff); + } + + dmFree(tmpBuf); + } + else + { + Sint16 t, p, value = 0, *sdata = (Sint16 *) srcData; + size_t ssize = srcSize; + while (ssize--) + { + if (ops & jsampSwapEndianess) + { + p = *sdata; + t = ((p >> 8) & 0xff) | ((p & 0xff) << 8); + } else + t = *sdata; + + if (ops & jsampDelta) + t = value = t + value; + + if (ops & jsampFlipSign) + t ^= 0x8000; + + *(sdata++) = t; + } + } + return TRUE; +} + + +/* Allocates a new module structure or returns errorvalue if failed. + * Memory is allocated only for the basic structure. Sample- and pattern + * areas must be allocated separately with appropriate routines. + */ +JSSModule *jssAllocateModule(void) +{ + int i; + JSSModule *module; + + // Allocate module structure + module = dmMalloc0(sizeof(JSSModule)); + if (module == NULL) + return NULL; + + // Initialize structure + for (i = 0; i < jsetNChannels; i++) + module->defPanning[i] = jchPanMiddle; + + for (i = 0; i < jsetMaxOrders; i++) + module->orderList[i] = jsetOrderEnd; + + // Allocate mutex +#ifdef JSS_SUP_THREADS + module->mutex = dmCreateMutex(); +#endif + + return module; +} + + +/* Frees a given module structure, freeing all memory areas + * that were allocated for it (including patterns, samples, etc.) + */ +int jssFreeModule(JSSModule * module) +{ + int i; + + if (module == NULL) + return DMERR_NULLPTR; + + // Free strings +#ifndef JSS_LIGHT + dmFree(module->moduleName); + dmFree(module->trackerName); +#endif + + // Free patterns + for (i = 0; i < module->npatterns; i++) + { + if (module->patterns[i]) + { + JSSPattern *pat = module->patterns[i]; + dmFree(pat->data); + dmFree(pat); + module->patterns[i] = NULL; + } + } + + // Free instruments + for (i = 0; i < module->ninstruments; i++) + { + if (module->instruments[i]) + { + JSSInstrument *inst = module->instruments[i]; +#ifndef JSS_LIGHT + dmFree(inst->desc); +#endif + dmFree(inst->data); + dmFree(inst); + module->instruments[i] = NULL; + } + } + + // Free extended instruments + for (i = 0; i < module->nextInstruments; i++) + { + if (module->extInstruments[i]) + { + JSSExtInstrument *ext = module->extInstruments[i]; +#ifndef JSS_LIGHT + dmFree(ext->desc); +#endif + dmFree(ext); + module->extInstruments[i] = NULL; + } + } + + // Free mutex +#ifdef JSS_SUP_THREADS + dmDestroyMutex(module->mutex); +#endif + + // Free the module structure + memset(module, 0, sizeof(JSSModule)); + dmFree(module); + + return DMERR_OK; +} + + +/* Allocates and initializes a internal pattern structure. + */ +JSSPattern *jssAllocatePattern(int nrows, int nchannels) +{ + int i, j; + JSSPattern *res; + JSSNote *pnote; + + // Check arguments + if (nrows <= 0 || nchannels <= 0) + JSSERROR(DMERR_INVALID_ARGS, NULL, "Invalid nrows=%i or nchannels=%i.\n", nrows, nchannels); + + // Allocate a pattern structure + res = dmMalloc0(sizeof(JSSPattern)); + if (res == NULL) + JSSERROR(DMERR_MALLOC, NULL, "Could not allocate pattern structure.\n"); + + // Allocate notedata + res->data = dmCalloc(nrows * nchannels, sizeof(JSSNote)); + if (res->data == NULL) + { + dmFree(res); + JSSERROR(DMERR_MALLOC, NULL, "Could not allocate pattern data (nrows=%i, nchannels=%i).\n", nrows, + nchannels); + } + + // Initialize + res->nrows = nrows; + res->nchannels = nchannels; + + pnote = res->data; + for (j = 0; j < nrows; j++) + { + for (i = 0; i < nchannels; i++) + { + pnote->note = pnote->instrument = pnote->volume = + pnote->effect = pnote->param = jsetNotSet; + + pnote++; + } + } + + // OK, return pointer to struct + return res; +} + + +/* Allocates and initializes internal "normal" instrument structure. + */ +JSSInstrument *jssAllocateInstrument(void) +{ + JSSInstrument *res; + + // Allocate a instrument structure + res = dmMalloc0(sizeof(JSSInstrument)); + if (res == NULL) + return NULL; + + return res; +} + + +/* Allocates and initializes "extended" instrument structure. + */ +JSSExtInstrument *jssAllocateExtInstrument(void) +{ + int i; + JSSExtInstrument *res; + + // Allocate a instrument structure + res = dmMalloc0(sizeof(JSSExtInstrument)); + if (res == NULL) + return NULL; + + for (i = 0; i < jsetNNotes; i++) + { + res->sNumForNotes[i] = jsetNotSet; + } + + return res; +}