Sunday, July 20, 2014

Hackaday Prize and MIDI2VC+ update

Hackaday Prize

I submitted the MIDI2VC project to the Hackaday Prize contest. I know that the MIDI2VC doesn't really qualify for the connected criteria. Connected meaning connected to the Internet. My interpretation of connectedness in this case is the connection between new and old, between digital and analogue. I have no aspiration of going to the moon, but a t-shirt or some electronics swag would be nice :)

MIDI2VC+ update

I received the MCU's for the MIDI2VC+ a while ago. I don't remember if I wrote about it, but it was hard sourcing the MCU for the project (PIC24FJ64GB004), so I ended up ordering a couple of samples from Microchip. A while after the samples arrived, I realised that I had ordered the wrong chips... I had ordered PIC24FJ64GA004! Those chips are almost pin compatible, but don't have the USB host capabilities I need. I've tried getting the right chips again, but still difficult. I ordered a couple from ebay, but they are not being shipped and no explanation from the seller (a chip shortage there as well?). So, I ended up ordering samples again. This time the right ones along with a couple of PIC24FJ64GB002, which can act as USB host, but has fewer pins (I thought the first chip was the one with lowest pin count, I guess I didn't do my homework). I might use those in the next version of the board. There will, by the way, be another board version. I realised I need to use an external crystal since to internal oscillator isn't precise enough for the USB standard.

Buggy Pickit 3

I tested out the MIDI2VC+ board with the chips I got from Microchip. I managed to put together a small hello world program that flashes the four LEDs nigthrider style! The program uses maximum clock speed, with internal oscillator, and interrupts.

I tried using the Pickit 3 for the MIDI2VC, but it seems to be so buggy that I ended up going back to the Pickit 2. It would probably had taken me half the time developing the knightrider program if I had used the Pickit 2 from the beginning. However, I can't use the Pickit 2 for debugging, so I may have to use 3 once in a while anyway. Pickit 3 bugs include:
  • Sometimes, not being able to identify the target device
  • Sometimes, not being able to program target  device
  • Not being able to power device two or more times in a row
  • Same code giving totally different results on different build and programming occasions
Hello knightrider code:
 /*@ignore@*/  
 #include <xc.h>  
 /*@end@*/  
 #ifdef __PIC24FJ256GB110__     //Defined by MPLAB when using 24FJ256GB110 device  
 _CONFIG1(JTAGEN_OFF & GCP_OFF & GWRP_OFF & COE_OFF & FWDTEN_OFF & ICS_PGx2)  
 _CONFIG2(IESO_OFF & FCKSM_CSDCMD & OSCIOFNC_OFF & POSCMOD_HS & FNOSC_PRIPLL & PLLDIV_DIV2 & IOL1WAY_ON)  
 _CONFIG3(WPCFG_WPCFGDIS & WPDIS_WPDIS) //Disable erase/write protect of all memory regions.  
 #elif __PIC24FJ256GA110__     //Defined by MPLAB when using 24FJ256GA110 device  
 _CONFIG1(JTAGEN_OFF & GCP_OFF & GWRP_OFF & COE_OFF & FWDTEN_OFF & ICS_PGx2)  
 _CONFIG2(FCKSM_CSDCMD & OSCIOFNC_OFF & POSCMOD_XT & FNOSC_PRI & IOL1WAY_ON)  
 _CONFIG3(WPCFG_WPCFGDIS & WPDIS_WPDIS) //Disable erase/write protect of all memory regions.  
 #elif __PIC24FJ64GA004__     //Defined by MPLAB when using 24FJ64GA004 device  
 _CONFIG1(JTAGEN_OFF & GCP_OFF & GWRP_OFF & COE_OFF & FWDTEN_OFF & ICS_PGx1)  
 _CONFIG2(FCKSM_CSDCMD & OSCIOFNC_OFF & POSCMOD_NONE & FNOSC_FRCPLL & I2C1SEL_SEC & IOL1WAY_ON)  
 #else     //Default to the PIC24FJ128GA010  
 // JTAG/Code Protect/Write Protect/Clip-on Emulation mode  
 // Watchdog Timer/ICD pins select  
 _CONFIG1(JTAGEN_OFF & GCP_OFF & GWRP_OFF & COE_OFF & FWDTEN_OFF & ICS_PGx2)  
 // Disable CLK switch and CLK monitor, OSCO or Fosc/2, HS oscillator,  
 // Primary oscillator  
 _CONFIG2(FCKSM_CSDCMD & OSCIOFNC_OFF & POSCMOD_XT & FNOSC_PRI)  
 #endif  
 int volatile LEDS_backward;  
 int volatile LEDS_index;  
 void __attribute__((__interrupt__, __auto_psv__)) _T1Interrupt(void) {  
   extern volatile int LEDS_backward;  
   extern volatile int LEDS_index;  
   LEDS_index = ((LEDS_index + 1) % 3);  
   LATC &= 0xFFF4;  
   LATB &= 0xFFFB;  
   if (LEDS_backward == 0) {  
     switch (LEDS_index) {  
       case (0):  
         LATB |= (1 << 2);  
         break;  
       case (1):  
         LATC |= (1 << 0);  
         break;  
       case (2):  
         LATC |= (1 << 1);  
         LEDS_backward = 1;  
         break;  
     }  
   }  
     else if (LEDS_backward == 1) {  
     switch (LEDS_index) {  
       case (0):  
         LATC |= (1 << 3);  
         break;  
       case (1):  
         LATC |= (1 << 1);  
         break;  
       case (2):  
         LATC |= (1 << 0);  
         LEDS_backward = 0;  
         break;  
     }  
   }  
   IFS0 = 0x0000;  
   return;  
 }  
 int main() {  
   extern volatile int LEDS_backward;  
   extern volatile int LEDS_index;  
   LEDS_backward = 0;  
   LEDS_index = 0;  
   TRISB = 0x00;  
   PORTB = 0x00;  
   TRISC = 0x00;  
   PORTC = 0xff;  
   IFS0 = 0x0000;  
   IEC0 = 0x0008;  
   T1CON = 0x8010;  
   TMR1 = 0x0000;  
   while (1) {  
   }  
   return 0;  
 }  

Monday, June 30, 2014

MIDI2VC, finished basic functionality

I've now added support for Pitch Bend to the MIDI2VC, which means the project is basically finished. The updated project is here.
 A demo video, with pitch bend, is below:
I thought about experimenting with the sleep mode of the PIC, to see if I can get the circuit a bit more efficient (probably not, since there is a linear regular on it...) My thought was that the PIC could go into sleep mode when it's waiting for an UART character. Seems though, that this function needs to receive a 0x0000 word to get out of sleep mode, and since I don't control the MIDI-device attached, I probably can't get that. Maybe there's a work around, we'll see....
Otherwise, it's time to start working on the MIDI2VC+.

Thursday, June 12, 2014

Synthesizer chopping sound

The chopping sound in the release phase I wrote about in the last post was actually from the DAC going to the lowest key. I coded this a while ago when I wanted to play without having an attack and release envelope. Now this is messing upp the release phase, so I removed the feature to let the DAC voltage level stay on the last played note. Sounds nice!

Tuesday, June 10, 2014

Actual synth sound + Attack and Release

Attack and Release

The last module for my simple synthesizer was an attack and release envelope generator to be driven by the gate out port of the MIDI2VC and connected to the VCA. I saw some designs that I thought where to complicated for now, so I made up my own very simple circuit:
Simple attack and release envelope generator
It's based on a comparator that source or drain current to C1. Right now it's half working. On the release I get an oscillation that sounds like a low frequency humping. Possibly this is caused by the emitter follower on the output. I'll look into it soon. I may also increase C1 to get a longer envelope.

Actual synth sound

So, this is what the synth looks like right now:
Messy analogue synthesizer

And this is what it sounds like:


Now I want to build some better synthesizer modules :)

Wednesday, May 7, 2014

MIDI2VC+ PCB

The PCB for the MIDI2VC+ has been ordered from http://oshpark.com/ . It will work as the MIDI2VC, with the addition of being a USB-host, so that one can connect a MIDI-USB device to it.

MIDI2VC+ PCB from Oshpark

Monday, May 5, 2014

Sunday, April 27, 2014

MIDI2VC and MIDI2VC+

MIDI2VC+

When I got my mini-midi-keyboard, I decided to add USB support to the MIDI2VC, since this is what most modern MIDI devices use. This new feature is quite complex to add. It needs and MCU with USB host capabilities. The simplest PIC I found with this feature was the PIC24FJ64GA004, which is a 44 pin 16-bit MCU. Obviously changing to this device will be a major change in the project, so I decided to name the new board MIDI2VC+. I'm working on the schematic and the layout right now, and as soon as I've sent the design to OshPark, I'll finish the MIDI2VC and release it as an open source hardware project.

I2C: 3.3V and 5V bus

When working on the new MIDI2VC+ design, I was bothered with the different supply voltage of the DAC and the new PIC. The new PIC is using CMOS (3.3V) levels and the DAC TTL (5V). This means a 3.3V I2C bus and a 5V I2C bus that needs to communicate. My first solution was using the PCA9517A, a bidirectional, level changing, bus repeater. This seemed all well and dandy, until I realised that I needed to order this part from RS Components, and the shipping would cost more than 10 times than the part. This went against my principle of making a project with cheap, and easy to source components.
 After doing some research I understood that sometimes it's possible to run different I2C level buses on the same voltage bus. Here's how it works. The I2C bus is an open drain bus. This means that the bus has pull up resistors to the higher voltage level. So if no one does anything on the bus, the bus sits at its high level. As soon as any device on the bus wants to communicate, it sinks current from the bus, making it go low, to  send a logic 1. For a logic 0 the device lets the bus go to the high level. The whole protocol is well explained on several places on the web...
 Lets look at our to devices then: 
The DAC is a five volt logic device. It sinks the bus down to 0.4V when signaling a low level. Thresholds are VIL = 0.3*5V = 1.5V and VIH = 0.7*5V = 3.5V.
The PIC is a 3.3V device, but it tolerates up to 5.5V on digital only pins (which we will use). It sinks the bus to 0V for a low level. It's thresholds are VIL = 0.3*3.3V = 0.99V and VIH = 0.7*3.3V = 2.31V.
Seems like the two devices can communicate over I2C despite the different logic levels!