@@ -1,38 +1,16 @@
/*
ChibiOS - Copyright (C) 2006..2015 Giovanni Di Sirio
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

#include "ch.h"
#include "hal.h"
#include "phi_lib/phi_lib.h"
#include "phi_lib/phi_bl_common.h"

#include "usbcfg.h"




#include "lcd.h"
#include "narvi_midi.h"

static uint8_t ii;

#define LINE_RS PAL_LINE(GPIOE, 14U) // MOSI
#define LINE_RW PAL_LINE(GPIOE, 13U) // MISO
#define LINE_E PAL_LINE(GPIOE, 12U) // CLK
#define LINE_A PAL_LINE(GPIOE, 11U) // D4 unused
/*===========================================================================*/
/* LCD configuration */
/*===========================================================================*/

/* Data PIN are connected from PC0 to PC7 */
#define LINE_RS PAL_LINE(GPIOE, 13U) // MISO
#define LINE_E PAL_LINE(GPIOE, 14U) // MOSI
#define LINE_A PAL_LINE(GPIOE, 14U) // UNUSED
#if !LCD_USE_4_BIT_MODE
#error sux
#endif
@@ -41,38 +19,11 @@ static uint8_t ii;
#define LINE_D6 PAL_LINE(GPIOE, 9U)
#define LINE_D7 PAL_LINE(GPIOE, 10U)

/*===========================================================================*/
/* LCD configuration */
/*===========================================================================*/

#if LCD_USE_DIMMABLE_BACKLIGHT
static const PWMConfig pwmcfg = {
100000, /* 100kHz PWM clock frequency. */
100, /* PWM period is 1000 cycles. */
NULL,
{
{PWM_OUTPUT_ACTIVE_HIGH, NULL},
{PWM_OUTPUT_DISABLED, NULL},
{PWM_OUTPUT_DISABLED, NULL},
{PWM_OUTPUT_DISABLED, NULL}
},
0,
0
};
#endif

static const lcd_pins_t lcdpins = {
LINE_RS,
LINE_RW,
LINE_E,
LINE_A,
{
#if !LCD_USE_4_BIT_MODE
LINE_D0,
LINE_D1,
LINE_D2,
LINE_D3,
#endif
LINE_D4,
LINE_D5,
LINE_D6,
@@ -86,11 +37,6 @@ static const LCDConfig lcdcfg = {
LCD_SET_FONT_5X10, /* Font 5x10 */
LCD_SET_2LINES, /* 2 lines */
&lcdpins, /* pin map */
#if LCD_USE_DIMMABLE_BACKLIGHT
&PWMD1, /* PWM Driver for back-light */
&pwmcfg, /* PWM driver configuration for back-light */
0, /* PWM channel */
#endif
100, /* Back-light */
};

@@ -116,8 +62,6 @@ static THD_FUNCTION(Thread2, arg) {
/* Initialization and main thread. */
/*===========================================================================*/

extern audio_state_t audio;


char boot_user_status[16];

@@ -209,81 +153,41 @@ int main(void) {
halInit();

force_bl = FALSE; // TODO
if (!force_bl) {
if (!force_bl) {
boot_user();
} else {
strcpy(boot_user_status, "Forced");
}

chSysInit();

lcdInit();
palSetLineMode(LINE_RS, PAL_MODE_OUTPUT_PUSHPULL | PAL_STM32_OSPEED_HIGHEST);
palSetLineMode(LINE_E, PAL_MODE_OUTPUT_PUSHPULL | PAL_STM32_OSPEED_HIGHEST);
lcdStart(&LCDD1, &lcdcfg);
lcdWriteString(&LCDD1, "PHI Narvi - BL", 0);
lcdWriteString(&LCDD1, boot_user_status, 40);


lcdInit();

#if LCD_USE_DIMMABLE_BACKLIGHT
/* Configuring Anode PIN as TIM1 CH1 alternate function. */
palSetLineMode(LINE_A, PAL_MODE_ALTERNATE(1));
#else
/* Configuring Anode PIN as TIM1 CH1 alternate function. */
palSetLineMode(LINE_A, PAL_MODE_OUTPUT_PUSHPULL |
PAL_STM32_OSPEED_HIGHEST);
#endif


/* Configuring RW, RS and E PIN as Output Push Pull. Note that Data PIN are
managed Internally */
palSetLineMode(LINE_RW, PAL_MODE_OUTPUT_PUSHPULL |
PAL_STM32_OSPEED_HIGHEST);
palSetLineMode(LINE_RS, PAL_MODE_OUTPUT_PUSHPULL |
PAL_STM32_OSPEED_HIGHEST);
palSetLineMode(LINE_E, PAL_MODE_OUTPUT_PUSHPULL |
PAL_STM32_OSPEED_HIGHEST);


lcdStart(&LCDD1, &lcdcfg);
lcdWriteString(&LCDD1, "NARVI BL", 0);
lcdWriteString(&LCDD1, boot_user_status, 40);


// ab_main_midi_init();
mduObjectInit(&MDU1);
mduStart(&MDU1, &midiusbcfg);

// ab_main_midi_init();
mduObjectInit(&MDU1);
mduStart(&MDU1, &midiusbcfg);

audioObjectInit(&audio);
narvi_midi_init();

/*
* Activates the USB driver and then the USB bus pull-up on D+.
* Note, a delay is inserted in order to not have to disconnect the cable
* after a reset.
*/
usbDisconnectBus(midiusbcfg.usbp);
chThdSleepMilliseconds(1000);
usbStart(midiusbcfg.usbp, &usbcfg);
usbConnectBus(midiusbcfg.usbp);

chThdCreateStatic(waThread2, sizeof(waThread2), NORMALPRIO + 10, Thread2, NULL);

/*
* Activates the USB driver and then the USB bus pull-up on D+.
* Note, a delay is inserted in order to not have to disconnect the cable
* after a reset.
*/
usbDisconnectBus(midiusbcfg.usbp);
chThdSleepMilliseconds(1000);
usbStart(midiusbcfg.usbp, &usbcfg);
usbConnectBus(midiusbcfg.usbp);



/*
* Creating the blinker threads.
*/
// codec_init();
chThdCreateStatic(waThread2, sizeof(waThread2),
NORMALPRIO + 10, Thread2, NULL);

// while (1) chThdSleepMilliseconds(10);



/*
* Normal main() thread activity, in this demo it just performs
* a shell respawn upon its termination.
*/
while (true) {
chThdSleepMilliseconds(500);
}
while (true) {
chThdSleepMilliseconds(500);
}
}

Large diffs are not rendered by default.

@@ -0,0 +1,41 @@
#ifndef NARVI_MIDI_H_
#define NARVI_MIDI_H_

#include "phi_lib/phi_midi.h"
#include "phi_lib/phi_bl_multiimg.h"

#ifdef __cplusplus
extern "C" {
#endif

enum {
NARVI_BL_MIDI_SYSEX_CMD_BL_START = PHI_MIDI_SYSEX_CMD_USER,
NARVI_BL_MIDI_SYSEX_CMD_BL_DATA,
NARVI_BL_MIDI_SYSEX_CMD_BL_DONE,
NARVI_BL_MIDI_SYSEX_CMD_BL_SERFLASH_START,
NARVI_BL_MIDI_SYSEX_CMD_BL_SERFLASH_DATA,
NARVI_BL_MIDI_SYSEX_CMD_BL_SERFLASH_DONE,
NARVI_BL_MIDI_SYSEX_CMD_BL_UPDATE_SELF_FROM_SERFLASH,
};

void narvi_midi_init(void);
void narvi_midi_in_handler(phi_midi_port_t port, const phi_midi_pkt_t * pkt);
void narvi_midi_in_sysex(phi_midi_port_t port, uint8_t cmd, const void * data, size_t data_len);
void narvi_midi_get_dev_info(phi_midi_sysex_dev_info_t * dev_info);
void narvi_midi_tx_pkt(phi_midi_port_t port, const phi_midi_pkt_t * pkt);
void narvi_midi_tx_sysex(phi_midi_port_t port, const uint8_t * data, size_t len);

void narvi_midi_bl_start(phi_midi_port_t port, const void * data, size_t data_len);
void narvi_midi_bl_data(phi_midi_port_t port, const void * data, size_t data_len);
void narvi_midi_bl_done(phi_midi_port_t port, const void * data, size_t data_len);

void narvi_midi_bl_serflash_start(phi_midi_port_t port, const void * data, size_t data_len);
void narvi_midi_bl_serflash_data(phi_midi_port_t port, const void * data, size_t data_len);
void narvi_midi_bl_serflash_done(phi_midi_port_t port, const void * data, size_t data_len);
void narvi_midi_bl_update_self_from_serflash(phi_midi_port_t port, const void * data, size_t data_len);

#ifdef __cplusplus
}
#endif

#endif /* NARVI_MIDI_H_ */
@@ -8,7 +8,7 @@
* NARVI Specific stuff
*****************************************************************************/

#define NARVI_HW_SW_VER PHI_HW_SW_VER(0, PHI_BL_HW_VER, PHI_BL_SW_VER)
#define NARVI_HW_SW_VER PHI_HW_SW_VER(1, PHI_BL_HW_VER, PHI_BL_SW_VER)
#define NARVI_DEV_ID PHI_BL_DEV_ID


Large diffs are not rendered by default.

@@ -1,130 +1,11 @@
/*
ChibiOS - Copyright (C) 2006..2015 Giovanni Di Sirio
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

#ifndef _USBCFG_H_
#define _USBCFG_H_

#include "phi_lib/phi_usb_midi.h"

extern const USBConfig usbcfg;

//extern BulkUSBDriver BDU1;
//extern const BulkUSBConfig bulkusbcfg;



extern MIDIUSBDriver MDU1;
extern const MIDIUSBConfig midiusbcfg;

/*
* Supported control requests from USB Audio Class
*/
#define UAC_REQ_SET_CUR 0x01
#define UAC_REQ_SET_MIN 0x02
#define UAC_REQ_SET_MAX 0x03
#define UAC_REQ_SET_RES 0x04
#define UAC_REQ_GET_CUR 0x81
#define UAC_REQ_GET_MIN 0x82
#define UAC_REQ_GET_MAX 0x83
#define UAC_REQ_GET_RES 0x84

#define UAC_FU_MUTE_CONTROL 0x01
#define UAC_FU_VOLUME_CONTROL 0x02

/*
* Audio playback events
*/
#define AUDIO_EVENT EVENT_MASK(0)
#define AUDIO_EVENT_PLAYBACK EVENT_MASK(1)
#define AUDIO_EVENT_MUTE EVENT_MASK(2)
#define AUDIO_EVENT_VOLUME EVENT_MASK(3)
#define AUDIO_EVENT_USB_STATE EVENT_MASK(4)



/*
* Audio parameters.
*/
#define AUDIO_SAMPLING_FREQUENCY 48000U
#define AUDIO_RESOLUTION 32U
#define AUDIO_SAMPLES_PER_FRAME (AUDIO_SAMPLING_FREQUENCY / 1000)

#define DAC_AUDIO_CHANNELS 2U
#define DAC_AUDIO_PACKET_SIZE (AUDIO_SAMPLES_PER_FRAME * DAC_AUDIO_CHANNELS \
* AUDIO_RESOLUTION / 8)
/* Because of samplerate feedback host can send more samples per frame */
#define DAC_AUDIO_MAX_PACKET_SIZE (DAC_AUDIO_PACKET_SIZE + 4)
#define DAC_AUDIO_BUFFER_SIZE (AUDIO_SAMPLES_PER_FRAME * DAC_AUDIO_CHANNELS * 8)

#if DAC_AUDIO_BUFFER_SIZE != (DAC_AUDIO_PACKET_SIZE * 2)
#error wtf
#endif


#define USB_AUDIO_CHANNELS 4U
#define USB_AUDIO_PACKET_SIZE (AUDIO_SAMPLES_PER_FRAME * USB_AUDIO_CHANNELS \
* AUDIO_RESOLUTION / 8)
/* Because of samplerate feedback host can send more samples per frame */
#define USB_AUDIO_MAX_PACKET_SIZE (USB_AUDIO_PACKET_SIZE + 16)
#define USB_AUDIO_BUFFER_SIZE (AUDIO_SAMPLES_PER_FRAME * USB_AUDIO_CHANNELS * 8)

#if USB_AUDIO_BUFFER_SIZE != (USB_AUDIO_PACKET_SIZE * 2)
#error wtf
#endif





/*
* USB Audio Class parameters
*/
#define AUDIO_PLAYBACK_ENDPOINT 0x01
#define AUDIO_FEEDBACK_ENDPOINT 0x02
#define MIDI_ENDPOINT 0x03
#define AUDIO_FEEDBACK_ENDPOINT 0x02
#define AUDIO_CONTROL_INTERFACE 0
#define AUDIO_STREAMING_INTERFACE 1
#define MIDI_STREAMING_INTERFACE 2

#define AUDIO_INPUT_UNIT_ID 1
#define AUDIO_FUNCTION_UNIT_ID 2
#define AUDIO_OUTPUT_UNIT_ID 3


typedef struct {

/* Audio events source */
event_source_t audio_events;

/* Audio playback occurs */
bool playback;
/* Samplerate feedback valid */
bool sof_feedback_valid;

/* Buffer underflows/overflows */
int buffer_errors;

/* Channel mute states */
bool mute[2];
/* Channel volumes in 8.8 format (dB) */
int16_t volume[2];
} audio_state_t;


#endif /* _USBCFG_H_ */

/** @} */
@@ -30,7 +30,7 @@ const SetupForm = Form.create()(
[
'Pulsar Heavy Industries CENX4 CENX4 MIDI',
'Pulsar Heavy Industries CENX4',
'PHI Narvi NarviCtrl',
'Pulsar Heavy Industries Narvi NarviCtrl',
].forEach((val) => {
if (!defaultInput && inputs.indexOf(val) !== -1)
{