AudioScience HPI Version_4.10.

HPI CobraNet HMI

HPI example that communicates to CobraNet HMI interface.

/******************************************************************************
$Header: /home/eliot/asi/repo/cvsrepo/Repository/drv/linux/test/asihpicn.c,v 1.13 2011/04/05 10:02:06 as-dxb Exp $

  Test Hardware Programming Interface (HPI) using HPI functions

  Usage: asihpicn --help

note to cleanup this file, use "astyle --style=linux -s4 asihpicn.c"
******************************************************************************/

#define SECONDS (1000/POLL_INTERVAL)
#define MINUTES (60*SECONDS)

#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <ctype.h>
#ifndef _MSC_VER
#include <unistd.h>
#endif
#include <getopt.h>
#ifdef __APPLE__
#include <hpi/hpi.h>
#include <hpi/hpidebug.h>
#else
#include <hpi.h>
#include <hpidebug.h>
#endif

#define verbose_printf if (verbose) printf

typedef struct {
        uint16_t wControlType;  // HPI_CONTROL_METER, _VOLUME etc
        uint16_t wSrcNodeType;
        uint16_t wSrcNodeIndex;
        uint16_t wDstNodeType;
        uint16_t wDstNodeIndex;
} hpi_control_t;

// local protos
static void HandleError(hpi_err_t err);

// global
#define BLOCK_SIZE 32768L       //30720L //6144 //12288 //16384 //19200 //9600
static uint8_t abBuffer[BLOCK_SIZE];
static short haveFiles = 0;

/* Option variables */
static uint32_t hmi_address = 1;
static uint32_t hmi_size = 4;
static uint32_t do_write = 0;
static uint32_t do_read = 0;
static uint32_t do_list = 0;
static uint32_t do_test = 0;
static int write_value = 0;
static int wAdapterIndex = 0;
static int verbose = 0;

static struct option long_options[] = {
        {"adapter", required_argument, 0, 'a'},
        {"list", no_argument, 0, 'l'},
        {"mi-address", required_argument, 0, 'm'},
        {"mi-size", required_argument, 0, 's'},
        {"write-dec", required_argument, 0, 'd'},
        {"write-hex", required_argument, 0, 'x'},
        {"test", no_argument, 0, 't'},
        {"verbose", no_argument, 0, 'v'},
        {"help", no_argument, 0, 'h'},
        {0, 0, 0, 0}
};

static const char *short_options = "a:ld:m:s:tvx:h?";

static const char *option_help[] = {
        "<adapter number> to test.",
        "List example set of HMI variables.",
        "<addr> hex HMI address.",
        "<count> HMI bytes to get.",
        "<decimal value> Write a value.",
        "<hex value> Write a value.",
        "Test code",
        "Verbose mode",
        "Show this text."
};

static void help(void)
{
        int i = 0;
        printf("\nASIHPICN - Cobranet HMI access");
        printf("\nUsage - asihpicn [options]\n");
        while (long_options[i].name != 0) {
                printf("--%s -%c %s\n",
                        long_options[i].name,
                        (char)(long_options[i].val), option_help[i]);
                i++;
        }
        exit(0);
}

static void parse_options(
        int argc,
        char *argv[]
)
{
        int c;
    /*********** Parse the command line options ***************/
        while (1) {
                // int this_option_optind = optind ? optind : 1;
                int option_index = 0;

                c = getopt_long(argc, argv, short_options,
                        long_options, &option_index);
                if (c == -1)
                        break;

                switch (c) {
                case 0:
                        printf("option %s", long_options[option_index].name);
                        if (optarg)
                                printf(" with arg %s", optarg);
                        printf("\n");
                        break;
                case 'a':
                        wAdapterIndex = atoi(optarg);
                        break;
                case 'm':
                        do_read = 1;
                        hmi_address = strtoul(optarg, (char **)NULL, 16);
                        break;
                case 's':
                        hmi_size = atoi(optarg);
                        break;
                case 'l':
                        do_list = 1;
                        break;
                case 't':
                        do_test = 1;
                        break;
                case 'v':
                        verbose = 1;
                        break;
                case 'x':
                        write_value = strtoul(optarg, (char **)NULL, 16);
                        do_write = 1;
                        break;
                case 'd':
                        write_value = strtoul(optarg, (char **)NULL, 10);
                        do_write = 1;
                        break;
                case '?':
                case 'h':
                        help();
                        break;

                default:
                        printf("?? getopt returned character code 0%o ??\n",
                                c);
                }
        }

        if (optind < argc) {
                // printf ("non-option ARGV-elements: ");
        }

}

static void byteSwap(uint8_t *b, unsigned int nBytes)
{
        unsigned int i=0;

        while(nBytes>4)  {
                unsigned char c0, c1, c2, c3;
                c3 = b[i];
                c2 = b[i+1];
                c1 = b[i+2];
                c0 = b[i+3];

                b[i] = c0;
                b[i+1] = c1;
                b[i+2] = c2;
                b[i+3] = c3;
                nBytes -= 4;
                i += 4;
        }
}
/************************************** MAIN ***********************/
int main(int argc, char *argv[])
{
        hpi_hsubsys_t *hSubSys;
        hpi_err_t err = 0;
        uint32_t dwVersion = 0;
        uint16_t wNumAdapters = 0;
        uint16_t awAdapterList[20];
        uint16_t wListLength = 20;
        uint16_t wVersion;
        uint32_t dwSerialNumber;
        uint16_t wType;
        uint16_t wNumOutStreams;
        uint16_t wNumInStreams;

        hpi_handle_t hMixer = 0;
        hpi_handle_t hControl;

        uint32_t i = 0;

        long testcount = 0;

        parse_options(argc, argv);

        verbose_printf
                ("********************************************************************\n");
        verbose_printf("\n** Test HPI using Functions **\n");

        // open subsystem and find adapters
        verbose_printf
                ("********************************************************************\n");
        verbose_printf("HPI_SubSysCreate\n");
        hSubSys = HPI_SubSysCreate();
        if (hSubSys == NULL) {
                printf("hSubSys==NULL\n");
                exit(1);
        }

        err = HPI_AdapterClose(hSubSys, wAdapterIndex);
        verbose_printf("HPI_AdapterClose \n");
        HandleError(err);

        // open 1st adapter
        err = HPI_AdapterOpen(hSubSys, wAdapterIndex);
        verbose_printf("HPI_AdapterOpen \n");
        HandleError(err);

        err = HPI_AdapterGetInfo(hSubSys,
                wAdapterIndex,
                &wNumOutStreams,
                &wNumInStreams, &wVersion, &dwSerialNumber, &wType);
        verbose_printf("HPI_AdapterGetInfo\n");
        HandleError(err);
        verbose_printf("Adapter ID=%4X Index=%d NumOutStreams=%d NumInStreams=%d S/N=%d\nHw Version %c%d DSP code version %03d\n", wType, wAdapterIndex, wNumOutStreams, wNumInStreams, dwSerialNumber, ((wVersion >> 3) & 0xf) + 'A',  // Hw version major
                wVersion & 0x7, // Hw version minor
                ((wVersion >> 13) * 100) + ((wVersion >> 7) & 0x3f)     // DSP code version
                );

        // open the mixer of this adapter
        err = HPI_MixerOpen(hSubSys, wAdapterIndex, &hMixer);
        verbose_printf("HPI_MixerOpen: handle=%X\n", hMixer);
        HandleError(err);

        verbose_printf("Get cobranet control\n");
        err = HPI_MixerGetControl(hSubSys, hMixer,
                HPI_SOURCENODE_COBRANET, 0, HPI_DESTNODE_COBRANET, 0,
                HPI_CONTROL_COBRANET, &hControl);
        HandleError(err);

        if (!err) {

#define BUFSIZE 100
                char cnData[BUFSIZE];
                uint32_t byteCount;
                unsigned int i;

                if (hmi_size > BUFSIZE)
                        hmi_size = BUFSIZE;

                memset(cnData, 0, BUFSIZE);

                if (do_write) {

                        printf("Write %#x to %#X\n", write_value,
                                hmi_address);
                        *((uint32_t *)&cnData[0]) = write_value;

                        err = HPI_Cobranet_HmiWrite(hSubSys,
                                hControl,
                                hmi_address, hmi_size, (uint8_t *)&cnData);

                        HandleError(err);

                }

                if( do_read ) {
                        verbose_printf("Read a value from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);

                        HandleError(err);

                        printf("%d bytes.  ", byteCount);
                        printf("Hex: %#X %#X ", *(int *)&cnData[0],
                                *(int *)&cnData[4]);
                        printf("Decimal: %u %u\n", *(int *)&cnData[0],
                                *(int *)&cnData[4]);
                        for (i = 0; i < byteCount; i++) {
                                printf("%02hhx ", cnData[i]);
                        }
                        printf("\n");
                }

                {
                        uint32_t status = 0, readable = 0, writeable = 0;
                        err = HPI_Cobranet_HmiGetStatus(hSubSys, hControl,
                                &status, &readable, &writeable);
                        HandleError(err);
                        printf("Cobranet status 0x%02X Readable=0x%04X Writeable=0x%04X\n", status, readable, writeable);
                }
                // list some HMI variables
                // "magic" HMI address codes from CobraNet Programmer's Reference v2.5
                if(do_list) {
                        unsigned int bundle;

                        // sysDescripton
                        hmi_address = 0x100000;
                        hmi_size = 84;
                        memset(cnData, 0, BUFSIZE);
                        verbose_printf("Read sysDescripton from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);
                        byteSwap(cnData,byteCount);
                        printf("sysDescription : %s\n",&cnData[4]);
                        HandleError(err);

                        // sysName
                        hmi_address = 0x100300;
                        hmi_size = 60;
                        memset(cnData, 0, BUFSIZE);
                        verbose_printf("Read sysName from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);
                        byteSwap(cnData,byteCount);
                        printf("sysName : %s\n",&cnData[4]);
                        HandleError(err);

                        // Tx1 bundle
                        hmi_address = 0x50100;
                        hmi_size = sizeof(bundle);
                        verbose_printf("Read txBundle (tx1) from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&bundle);
                        printf("txBundle[1] : %d\n",bundle);
                        HandleError(err);

                        // Tx1 submap
                        hmi_address = 0x50200;
                        hmi_size = 8 * sizeof(int);
                        memset(cnData, 0, BUFSIZE);
                        verbose_printf("Read tx1 submap from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);
                        for(i=0;i<8;i++)
                                printf("txSubMap (tx1) audio channel %d, audio routing channel %d\n",
                                        i,
                                        ((int *)&cnData)[i]
                                        );
                        HandleError(err);

                        // Rx1 bundle
                        hmi_address = 0x40100;
                        hmi_size = sizeof(bundle);
                        verbose_printf("Read rxBundle (rx1) from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&bundle);
                        printf("rxBundle[1] : %d\n",bundle);
                        HandleError(err);
                        // Rx1 submap
                        hmi_address = 0x40200;
                        hmi_size = 8 * sizeof(int);
                        memset(cnData, 0, BUFSIZE);
                        verbose_printf("Read rx1 submap from %#X\n", hmi_address);
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);
                        for(i=0;i<8;i++)
                                printf("rxSubMap (rx1) audio channel %d, audio routing channel %d\n",
                                        i,
                                        ((int *)&cnData)[i]
                                        );
                        HandleError(err);
                }
                // test HMI variable read/write
                // various test cases
                if( do_test ) {
                        int *o;

                        // 1. Read Rx1 submap, then swap the submap around and write it back.

                        printf("Swapping audio submap channels for Rx1\n");

                        hmi_address = 0x40200;
                        hmi_size = 8 * sizeof(int);
                        memset(cnData, 0, BUFSIZE);

                        // read submap
                        err = HPI_Cobranet_HmiRead(hSubSys,
                                hControl,
                                hmi_address, hmi_size, &byteCount, (uint8_t *)&cnData);
                        HandleError(err);

                        // swap audio routing channels
                        o = (int *)&cnData;
                        for(i=0; i<4; i++) {
                                int t;
                                t = o[i*2];
                                o[i*2] = o[i*2+1];
                                o[i*2+1] = t;
                        }

                        // write submap
                        err = HPI_Cobranet_HmiWrite(hSubSys,
                                hControl,
                                hmi_address, hmi_size, (uint8_t *)&cnData);
                        HandleError(err);
                }
        }

        err = HPI_MixerClose(hSubSys, hMixer);
        verbose_printf("\nHPI_MixerClose\n");
        HandleError(err);

        err = HPI_AdapterClose(hSubSys, wAdapterIndex);
        verbose_printf("HPI_AdapterClose\n");
        HandleError(err);

        HPI_SubSysFree(hSubSys);
        return 0;
}

/****************************** HandleError **********************/
static int getch(void)
{
        return getchar();
}

static void HandleError(hpi_err_t err)
{
        char szError[256];
        char nK = 0;

        if (err) {
                HPI_GetErrorText(err, szError);
                printf("ERROR %d %s\n", err, szError);
                printf("press Enter to continue, (q,Enter) to exit...\n");
                nK = getch();
                if (nK == 'q')
                        exit(0);
        }
}
/* END_OF_CODE */