Re: [stella] TIA Audio Polynomials

Subject: Re: [stella] TIA Audio Polynomials
From: Adam Wozniak <adam@xxxxxxxxxxxxxxxx>
Date: Fri, 21 Nov 2003 14:50:24 -0800 (PST)
This produces raw PCM audio at 31.4 KHz.  When I play it back at 31.4 KHz
is sounds pretty close to the actual console I sampled.  All the tools I
have to convert from 31.4 KHz -> 44.1 KHz make it sound pretty bad though.

Maybe somebody else can pick it up from here...



#include <stdio.h>

// sound.c
// version 0.0
//
// Copyright (c) 2003 Adam Wozniak (adam@xxxxxxxxxxxxxxxx)
// All Rights Reserved
//
// Permission granted to freely copy and use for any purpose, provided
// this copyright header remains intact.

// Produces 1 second of audio with a base frequency of 31400 Hz

static const int poly0[] = {
        1, -1 };
static const int poly1[] = {
        1, 1, -1 };
static const int poly2[] = {
        16, 15, -1 };
static const int poly4[] = {
        1, 2, 2, 1, 1, 1, 4, 3, -1 };
static const int poly5[] = {
        1, 2, 1, 1, 2, 2, 5, 4, 2, 1, 3, 1, 1, 1, 1, 4,
        -1 };
static const int poly9[] = {
        1, 4, 1, 3, 2, 4, 1, 2, 3, 2, 1, 1, 1, 1, 1, 1,
        2, 4, 2, 1, 4, 1, 1, 2, 2, 1, 3, 2, 1, 3, 1, 1,
        1, 4, 1, 1, 1, 1, 2, 1, 1, 2, 6, 1, 2, 2, 1, 2,
        1, 2, 1, 1, 2, 1, 6, 2, 1, 2, 2, 1, 1, 1, 1, 2,
        2, 2, 2, 7, 2, 3, 2, 2, 1, 1, 1, 3, 2, 1, 1, 2,
        1, 1, 7, 1, 1, 3, 1, 1, 2, 3, 3, 1, 1, 1, 2, 2,
        1, 1, 2, 2, 4, 3, 5, 1, 3, 1, 1, 5, 2, 1, 1, 1,
        2, 1, 2, 1, 3, 1, 2, 5, 1, 1, 2, 1, 1, 1, 5, 1,
        1, 1, 1, 1, 1, 1, 1, 6, 1, 1, 1, 2, 1, 1, 1, 1,
        4, 2, 1, 1, 3, 1, 3, 6, 3, 2, 3, 1, 1, 2, 1, 2,
        4, 1, 1, 1, 3, 1, 1, 1, 1, 3, 1, 2, 1, 4, 2, 2,
        3, 4, 1, 1, 4, 1, 2, 1, 2, 2, 2, 1, 1, 4, 3, 1,
        4, 4, 9, 5, 4, 1, 5, 3, 1, 1, 3, 2, 2, 2, 1, 5,
        1, 2, 1, 1, 1, 2, 3, 1, 2, 1, 1, 3, 4, 2, 5, 2,
        2, 1, 2, 3, 1, 1, 1, 1, 1, 2, 1, 3, 3, 3, 2, 1,
        2, 1, 1, 1, 1, 1, 3, 3, 1, 2, 2, 3, 1, 3, 1, 8,
        -1 };
static const int poly68[] = {
        5, 6, 4, 5, 10, 5, 3, 7, 4, 10, 6, 3, 6, 4, 9, 6, -1 };
static const int poly465[] = {
        2, 3, 2, 1, 4, 1, 6, 10, 2, 4, 2, 1, 1, 4, 5,
        9, 3, 3, 4, 1, 1, 1, 8, 5, 5, 5, 4, 1, 1, 1,
        8, 4, 2, 8, 3, 3, 1, 1, 7, 4, 2, 7, 5, 1, 3,
        1, 7, 4, 1, 4, 8, 2, 1, 3, 4, 7, 1, 3, 7, 3,
        2, 1, 6, 6, 2, 2, 4, 5, 3, 2, 6, 6, 1, 3, 3,
        2, 5, 3, 7, 3, 4, 3, 2, 2, 2, 5, 9, 3, 1, 5,
        3, 1, 2, 2, 11, 5, 1, 5, 3, 1, 1, 2, 12, 5, 1,
        2, 5, 2, 1, 1, 12, 6, 1, 2, 5, 1, 2, 1, 10, 6,
        3, 2, 2, 4, 1, 2, 6, 10, -1 };
static const int divisors[] = {
        1, 1, 15, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 3, 1 };
static const int *polys[] = {
        poly0, poly4, poly4, poly465,
        poly1, poly1, poly2, poly5,
        poly9, poly5, poly2, poly0,
        poly1, poly1, poly2, poly68 };

// structure to hold state information, so successive calls to TIAfill
// will not sound poppy.  Be sure to clear everything to zero when changing
// C or F

struct state
{
        int offset, count, f;
        char last;
};

static void TIAfill(int F, int V, int C, char *buf, int size, struct state *s)
{
        int value;

        while (size)
        {
                s->f++;
                if (s->f == divisors[C] * (F+1))
                {
                        const int *poly = polys[C];
                        s->f = 0;

                        s->count++;
                        if (s->count == poly[s->offset])
                        {
                                s->offset++;
                                s->count = 0;
                                if (poly[s->offset] == -1)
                                {
                                        s->offset = 0;
                                }
                        }
                        s->last = ! (s->offset & 0x01);
                }

                *buf = s->last ? (V << 3): 0;

                buf++;
                size--;
        }
}

void main(int argc, char **argv)
{
        char buf[31400];
        struct state s;
        int i;

        // be sure to reset s to all zeros whenever C, F, or V change
        s.offset = 0;
        s.count = 0;
        s.last = 0;
        s.f = 0;

        // usage
        if (argc != 4)
        {
                fprintf(stderr, "Usage: %s <F:0-31> <V:0-15> <C:0-15>\n", argv[0]);
                exit(-1);
        }

        // fill a buffer
        TIAfill(atoi(argv[1]),
                atoi(argv[2]),
                atoi(argv[3]),
                buf, sizeof(buf), &s);

        // write it to stdout
        write(1, buf, sizeof(buf));
}

-- 
adam@xxxxxxxxxxxxxxxx        http://cuddlepuddle.org/~adam/pgp.html
Will code for food.          http://cuddlepuddle.org/~adam/resume.html
"The dinosaurs are not around today because they did not have a space program."
  -- Arthur C. Clarke

----------------------------------------------------------------------------------------------
Archives (includes files) at http://www.biglist.com/lists/stella/archives/
Unsub & more at http://www.biglist.com/lists/stella/


Current Thread