// http://blog.bitheap.net/2012/03/ft232r-bitbang-mode-is-broken.html
// scp -rCp root@192.168.30.1:/home/public/de/killig/sven/FTDI/* . && gcc -o square_wave square_wave.c -lftdi && ./square_wave s:0x0403:0x6014:FTVO7C1X

#include <stdio.h>
#include <string.h>
#include <ftdi.h>


struct ftdi_context *ftdic;
uint8_t data[25600];
uint8_t data2[25600];
int m_i;


void RCLtransmit(int nHighPulses, int nLowPulses) {
    /*digitalWrite(RCLpin, HIGH);
    delayMicroseconds( 350 * nHighPulses);
    digitalWrite(RCLpin, LOW);
    delayMicroseconds( 350 * nLowPulses);*/
    int j;
    for(j=1; j<=nHighPulses; j++) data[m_i++]=255;
    for(j=1; j<=nLowPulses; j++)  data[m_i++]=0;
printf("m_i=%i\n", m_i);
}


void RCLswitch(uint16_t code) {
	int nRepeat;
    for (nRepeat=0; nRepeat<60; nRepeat++) {
m_i=0;
    	int i;
        for (i=4; i<16; i++) {
            RCLtransmit(1,3);
            if (((code << (i-4)) & 2048) > 0) {
                RCLtransmit(1,3);
            } else {
                RCLtransmit(3,1);
            }
        }
        RCLtransmit(1,31);
ftdi_write_data(&ftdic, data, m_i);
ftdi_read_data(&ftdic, data2, m_i);
    }
}


void delay(int ms) {
	sleep(ms/1000);
}


void loop() {
    RCLswitch(0b111000010001);  // DIPs an Steckdose:123C  An:01
    delay(2000);

    RCLswitch(0b111000010010);  // DIPs an Steckdose:123C Aus:10
    delay(2000);
}


int main(int argc, char **argv)
{
#define BAUDRATE 183
//  ftdi_context ftdic;
int ret;
  ftdi_init(&ftdic);

//  if(ftdi_usb_open_desc(&ftdic, 0x0403, 0x6001, NULL, NULL) < 0)
  if((ret=ftdi_usb_open_string(&ftdic, argv[1])) < 0)
  {
    fprintf(stderr, "ftdi_usb_open_string failed: %s %i\n",
      ftdi_get_error_string(&ftdic), ret);
    exit(1);
  }


  if(ftdi_set_baudrate(&ftdic, BAUDRATE) < 0)
  {
    fprintf(stderr, "ftdi_set_baudrate failed: %s\n",
      ftdi_get_error_string(&ftdic));
    exit(1);
  }

printf("baudrate:%i\n", ftdic->baudrate);


  if(ftdi_set_bitmode(&ftdic, 255, BITMODE_SYNCBB) < 0)
  {
    fprintf(stderr, "ftdi_set_bitmode failed: %s\n",
      ftdi_get_error_string(&ftdic));
    exit(1);
  }


  if(ftdi_set_baudrate(&ftdic, BAUDRATE) < 0)
  {
    fprintf(stderr, "ftdi_set_baudrate failed: %s\n",
      ftdi_get_error_string(&ftdic));
    exit(1);
  }

printf("baudrate:%i\n", ftdic->baudrate);


  for(m_i=0; m_i<sizeof(data); m_i++)
//    data[i] = i&(1<<0)?1<<7:0; // FT232UM J2-14/AD7
//    data[i] = i&(1<<0)?1<<4:0; // uUSB-CE5 DTR
    data[m_i] = m_i&(1<<0)?1<<0:0; // uUSB-CE5 TX

  for(;;)
  {
    /*ftdi_write_data(&ftdic, data, sizeof(data));
    ftdi_read_data(&ftdic, data2, sizeof(data2));*/
loop();
  }

  return 0;
}
