// Copyright 2011 Google Inc. All Rights Reserved.
// Author: qianzhang@google.com (Qian Zhang)

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <inttypes.h>
#include "utility.h"
#include "channel_buffer.h"
#include "libhdhomerun/hdhomerun.h"
#include "hdhomerun_tuner.h"
#include "hdhomerun_dev.h"
#include "sagelog.h"

#define PARSE_TIMEOUT 2
#define CHANNE_SCAN_SRC   "227.0.0.1"
#define CHANNEL_SCAN_PORT  6069
static volatile sig_atomic_t sigabort_flag = FALSE;
static volatile sig_atomic_t siginfo_flag = FALSE;
static const char* map_tbl[] ={ "us-bcast", "us-cable", "us-hrc", "us-irc", "au-bcast", "tw-bcast", "eu-bcast", 0x0 };

static void sigabort_handler(int arg)
{
  sigabort_flag = TRUE;
}

static void siginfo_handler(int arg)
{
  siginfo_flag = TRUE;
}

static void register_signal_handlers(sig_t sigpipe_handler, sig_t sigint_handler, sig_t siginfo_handler)
{
#if defined(SIGPIPE)
  signal(SIGPIPE, sigpipe_handler);
#endif
#if defined(SIGINT)
  signal(SIGINT, sigint_handler);
#endif
#if defined(SIGINFO)
  signal(SIGINFO, siginfo_handler);
#endif
}

//channel format: map:us-cable,auto:68
void* open_hdhr( char* name )
{
  struct hdhomerun_device_t *hd;
  hd = hdhomerun_device_create_from_str( name, NULL);
  return hd;
}
void close_hdhr( void* device )
{
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  if ( hd ) {
    hdhomerun_device_stream_stop( hd );
    hdhomerun_device_destroy( hd );
  }
}

int tune_channel( void* device, char *channel, char *program, char* stream_target )
{
  char channel_str[32]="auto:";
  char vchannel_str[16];
  char channel_map[32];
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  struct hdhomerun_channel_list_t *channel_list=NULL;
  int ret;

  if ( hd == NULL ) {
    printf( "hdhomerun invalid handle\n");
    return -1;
  }

  if ( !get_string_by_name( channel, "vchan", vchannel_str, sizeof(vchannel_str), NULL ) ) {
    vchannel_str[0] = 0x0;

    if ( !get_string_by_name( channel, "auto", channel_str+5, sizeof(channel_str)-5, NULL ) ) {
      printf("hdhomerun %p invalid channel %s\n", device, channel );
      return -1;
    }
    if ( !get_string_by_name( channel, "map", channel_map, sizeof(channel_map), NULL ) ) {
      printf("hdhomerun %p invalid channel map %s\n", device, channel );
      strncpy( channel_map, "us-cable", sizeof(channel_map) );
    }
    if ( program[0] == 0x0 ) {
      printf("hdhomerun %p invalid channel program %s\n", device, program );
      return -1;
    }
    channel_list = hdhomerun_channel_list_create( channel_map );
    if ( channel_list == NULL ) {
      printf( "hdhomerun failed to create channel map\n");
      return -1;
    }
    ret = hdhomerun_device_set_tuner_channelmap( hd, channel_map );
    if ( ret < 0 )
      printf( "hdhomerun failed to set tuner channel map %s\n", channel_map );

    ret = hdhomerun_device_set_tuner_channel( hd, channel_str );
    if ( ret < 0 )
      printf("hdhomerun tuning failed:%s ret:%d\n", channel_str, ret );

    ret = hdhomerun_device_set_tuner_program( hd, program );
    if ( ret <= 0 )
      printf( "hdhomerun failed set program:%s ret:%d\n", program, ret );
  } else {
    ret = hdhomerun_device_set_tuner_vchannel( hd, vchannel_str );
    if ( ret < 0 )
      printf("hdhomerun tuning failed: vchannel:%s ret:%d\n", vchannel_str, ret );
  }

  char target[64];
  snprintf( target, sizeof(target), "%s ttl-2",stream_target );
  ret = hdhomerun_device_set_tuner_target( hd, target );
  if ( ret < 0 ) {
    printf( "hdhomerun failed set target %s  ret:%d\n", target, ret );
  }
  if ( channel_list )
    hdhomerun_channel_list_destroy( channel_list );

  return ret;
}

//channel format: map:us-cable,auto:68
int stop_channel( void* device )
{
  int ret;
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  if ( hd == NULL ) {
    printf( "hdhomerun invalid handle\n");
    return -1;
  }

  ret = hdhomerun_device_set_tuner_channel( hd, "none" );
  if ( ret < 0 ) {
    printf( "hdhomerun failed set channel none to stop streaming  ret:%d\n", ret );
  }

  ret = hdhomerun_device_set_tuner_vchannel( hd, "none" );
  if ( ret < 0 ) {
    printf( "hdhomerun failed set vchannel none to stop streaming  ret:%d\n", ret );
  }

  ret = hdhomerun_device_set_tuner_target( hd, "none" );
  if ( ret < 0 ) {
    printf( "hdhomerun failed set target none to stop streaming  ret:%d\n", ret );
  }

  return ret;
}

char* get_unit_name( struct hdhr_tuner_t *ht, char* name, int size )
{
  char* p = strchr( ht->name, '-' );
  if ( p != NULL ) {
    int len = p - ht->name;
    strncpy( name, ht->name, len );
    name[len] = 0x0;
    return name;
  }
  name[ 0 ] = 0x0;
  return name;
}

static char* ip4_address( int ip4, char *buf, int size )
{
  snprintf( buf, size, "%u.%u.%u.%u",
    (unsigned int)(ip4 >> 24) & 0xFF, (unsigned int)(ip4 >> 16) & 0xFF,
    (unsigned int)(ip4 >> 8) & 0xFF, (unsigned int)(ip4 >> 0) & 0xFF  );
  return buf;
}

int discover_device( struct hdhr_tuner_t *ht, int max_ht_num )
{
  int i, k, num = 0;
  struct hdhomerun_discover_device_t *device_info = malloc( max_ht_num * sizeof(struct hdhomerun_discover_device_t) );
  int ret = hdhomerun_discover_find_devices_custom(0, HDHOMERUN_DEVICE_TYPE_TUNER, -1, device_info, 16);
  if ( ret <= 0 ) {
    free( device_info );
    return 0;
  }
  //printf( "found %d hdhomerun device\n", ret );
  for ( i = 0; i<ret; i++ ) {
    //printf( "ip:%x type:%x id:%x num:%d\n", device_info[i].ip_addr, device_info[i].device_type, device_info[i].device_id,
    //    device_info[i].tuner_count );
    for ( k = 0; k<device_info[i].tuner_count && num < max_ht_num; k++ ) {
      snprintf( ht[num].name, sizeof(ht[num].name), "%X-%d", device_info[i].device_id, k );
      ip4_address( device_info[i].ip_addr, ht[num].ip, sizeof(ht[num].ip) );
      ht[num].type = device_info[i].device_type;
      ht[num].cc_tuner = 0;
      ht[num].model[0] = 0;
      num++;
    }
  }
  free( device_info );
  return num;
}

static char *get_tune_string( char* result, char* tune_str, int tune_str_len )
{
  int i = 0;
  int ch;
  while ( map_tbl[i][0] ) {
    if ( get_int_val_by_name( result, map_tbl[i], &ch, NULL ) > 0 ) {
      snprintf( tune_str, tune_str_len, "map:%s|auto:%d", map_tbl[i], ch );
      return tune_str;
    }
    i++;
  }
  return "";
}

static int get_tune_channel( char* result )
{
  int i = 0;
  int ch;
  while ( map_tbl[i][0] ) {
    if ( get_int_val_by_name( result, map_tbl[i], &ch, NULL ) > 0 ) {
      return ch;
    }
    i++;
  }
  return 0;
}

int scan_all( void* device, struct channel_entry_t *ce, int ce_num )
{
  int found_channel = 0;
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  if ( hd == NULL ) {
    printf( "hdhomerun invalid handle\n");
    return -1;
  }

  char *ret_error;
  if (hdhomerun_device_tuner_lockkey_request(hd, &ret_error) <= 0) {
    fprintf(stderr, "failed to lock tuner\n");
    if (ret_error) {
      fprintf(stderr, "%s\n", ret_error);
    }
    return -1;
  }

  hdhomerun_device_set_tuner_target(hd, "none");

  char *channelmap;
  if (hdhomerun_device_get_tuner_channelmap(hd, &channelmap) <= 0) {
    fprintf(stderr, "failed to query channelmap from device\n");
    return -1;
  }

  const char *channelmap_scan_group = hdhomerun_channelmap_get_channelmap_scan_group(channelmap);
  if (!channelmap_scan_group) {
    fprintf(stderr, "unknown channelmap '%s'\n", channelmap);
    return -1;
  }

  if (hdhomerun_device_channelscan_init(hd, channelmap_scan_group) <= 0) {
    fprintf(stderr, "failed to initialize channel scan\n");
    return -1;
  }

  register_signal_handlers(sigabort_handler, sigabort_handler, siginfo_handler);

  int ret = 0;
  while (!sigabort_flag && found_channel < ce_num ) {
    struct hdhomerun_channelscan_result_t result;
    char tune_str[32];
    char channel_name[32];
    int channel_num;
    ret = hdhomerun_device_channelscan_advance( hd, &result );
    if (ret <= 0) {
      break;
    }

    ret = hdhomerun_device_channelscan_detect( hd, &result );
    if (ret < 0) {
      break;
    }
    if (ret == 0) {
      continue;
    }
    if ( 0 )
    printf("LOCK: %s %s (ss=%u snq=%u seq=%u)\n", get_tune_string( result.channel_str, tune_str, sizeof(tune_str)),
      result.status.lock_str, result.status.signal_strength,
      result.status.signal_to_noise_quality, result.status.symbol_error_quality
    );

    channel_num = get_tune_channel( result.channel_str );
    int i;
    for (i = 0; i < result.program_count; i++) {
      struct hdhomerun_channelscan_program_t *program = &result.programs[i];
      if ( strstr( program->program_str, "encrypted" ) == NULL ) {
        int program_id = atoi( program->program_str );

        if ( !get_string_by_token( program->program_str, 2, channel_name, sizeof(channel_name), NULL ) ) {
          if ( !get_string_by_token( program->program_str, 1, channel_name, sizeof(channel_name), NULL ) )
            snprintf( channel_name, sizeof(channel_name), "%d.%d", channel_num, i );
          else {
            if ( !strcmp(channel_name, "0" ) )
              snprintf( channel_name, sizeof(channel_name), "%d.%d", channel_num, i );
          }
        }
        snprintf( ce->dev_tuning, sizeof(ce->dev_tuning), "%s prog:%d", get_tune_string( result.channel_str, tune_str, sizeof(tune_str) ),
                 program_id );
        strncpy( ce->ch_name, channel_name, sizeof(ce->ch_name) );
        strncpy( ce->dev_name, device, sizeof(ce->dev_name) );
        ce->ch = found_channel;
        ce->frq = result.frequency;
        ce->av_inf[0] = 0x0;
        ce++;
        if ( ++found_channel >= ce_num )
          break;

        printf("o");
      }
    }

    printf( "." ); fflush( stdout );
  }

  hdhomerun_device_tuner_lockkey_release(hd);

  if (ret < 0) {
    fprintf(stderr, "communication error sending request to hdhomerun device\n");
  }
  return found_channel;
}


struct vchan_tbl_t* create_vchan_tbl( struct hdhr_tuner_t *ht )
{
  struct vchan_tbl_t *vt = malloc( sizeof( struct vchan_tbl_t ));
  vt->ht = *ht;
  vt->channel_size = 500;
  vt->channel_num = 0;
  vt->vchan = malloc( sizeof(struct vchan_t )*vt->channel_size );
  memset( vt->vchan, 0x0, sizeof(struct vchan_t )*vt->channel_size );
  return vt;
}

void release_vchan_tbl( struct vchan_tbl_t *vt )
{
  if ( vt->vchan );
  free( vt->vchan );
  free( vt );
}

int grow_vhcan_tbl( struct vchan_tbl_t *vt )
{
  int new_channel_size = vt->channel_size + 100;
  struct vchan_t * new_vchan_list = malloc( sizeof(struct vchan_t)*new_channel_size );
  if ( new_vchan_list == NULL )
    return 0;
  memcpy( new_vchan_list, vt->vchan, vt->channel_size*sizeof(struct vchan_t) );
  free( vt->vchan );
  vt->vchan = new_vchan_list;
  vt->channel_size = new_channel_size;
  return 1;
}

int tuner_input_sharing( struct hdhr_tuner_t *ht1, struct hdhr_tuner_t *ht2 )
{
  if ( ht1->cc_tuner == 1 && !strcmp( ht1->ip, ht2->ip ) )
    return 1;
  return 0;
}


#ifdef TEST_APP
static int scan_channel( void* device, int index, struct channel_entry_t *ce, int ce_channel_num, int ce_num )
{
  int found_channel = 0;
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  if ( hd == NULL ) {
    printf( "hdhomerun invalid handle\n");
    return -1;
  }

  char *ret_error;
  if (hdhomerun_device_tuner_lockkey_request(hd, &ret_error) <= 0) {
    fprintf(stderr, "failed to lock tuner\n");
    if (ret_error) {
      fprintf(stderr, "%s\n", ret_error);
    }
    return -1;
  }

  hdhomerun_device_set_tuner_target(hd, "none");

  char *channelmap;
  if (hdhomerun_device_get_tuner_channelmap(hd, &channelmap) <= 0) {
    fprintf(stderr, "failed to query channelmap from device\n");
    return -1;
  }

  const char *channelmap_scan_group = hdhomerun_channelmap_get_channelmap_scan_group(channelmap);
  if (!channelmap_scan_group) {
    fprintf(stderr, "unknown channelmap '%s'\n", channelmap);
    return -1;
  }

  if (hdhomerun_device_channelscan_init(hd, channelmap_scan_group) <= 0) {
    fprintf(stderr, "failed to initialize channel scan\n");
    return -1;
  }

  register_signal_handlers(sigabort_handler, sigabort_handler, siginfo_handler);

  int ret = 0, i;
  do {
    struct hdhomerun_channelscan_result_t result;
    char tune_str[32];
    char channel_name[32];
    int channel_num;
    ret = hdhomerun_device_channelscan_at( hd, index, &result );
    //ret = hdhomerun_device_channelscan_advance( hd, &result );
    if (ret <= 0) {
      break;
    }
    /* skip dumplicated channel*/
    for ( i = 0; i<ce_channel_num; i++ ) {
      if ( ce->frq == result.frequency )
        break;
    }
    if ( ce->frq == result.frequency )
      break;
    ret = hdhomerun_device_channelscan_detect( hd, &result );
    if (ret < 0) {
      break;
    }
    if (ret == 0) {
      continue;
    }

    if ( 0 )
    printf("LOCK: %s %s (ss=%u snq=%u seq=%u)\n", get_tune_string( result.channel_str, tune_str, sizeof(tune_str)),
      result.status.lock_str, result.status.signal_strength,
      result.status.signal_to_noise_quality, result.status.symbol_error_quality
    );

    channel_num = get_tune_channel( result.channel_str );
    for ( i = 0; i < result.program_count; i++) {
      struct hdhomerun_channelscan_program_t *program = &result.programs[i];
      if ( strstr( program->program_str, "encrypted" ) == NULL ) {
        int program_id = atoi( program->program_str );

        if ( !get_string_by_token( program->program_str, 2, channel_name, sizeof(channel_name), NULL ) ) {
          if ( !get_string_by_token( program->program_str, 1, channel_name, sizeof(channel_name), NULL ) )
            snprintf( channel_name, sizeof(channel_name), "%d.%d", channel_num, i );
          else {
            if ( !strcmp(channel_name, "0" ) )
              snprintf( channel_name, sizeof(channel_name), "%d.%d", channel_num, i );
          }
        }
        struct channel_entry_t *ce_p = &ce[ce_channel_num];
        snprintf( ce->dev_tuning, sizeof(ce->dev_tuning), "%s prog:%d", get_tune_string( result.channel_str, tune_str, sizeof(tune_str) ),
                 program_id );
        strncpy( ce_p->ch_name, channel_name, sizeof(ce_p->ch_name) );
        strncpy( ce_p->dev_name, device, sizeof(ce_p->dev_name) );
        ce_p->ch = found_channel+ce_channel_num;
        ce_p->frq = result.frequency;
        ce_p->av_inf[0] = 0x0;
        char stream_tar[32];
        snprintf( stream_tar, sizeof(stream_tar), "udp://%s:%u", CHANNE_SCAN_SRC, CHANNEL_SCAN_PORT );
        ret = tune_channel( hd, ce_p->dev_tuning, "", stream_tar );
        if ( ret > 0 )
          ret = parse_avinf( CHANNE_SCAN_SRC, CHANNEL_SCAN_PORT, ce_p->av_inf, sizeof(ce_p->av_inf), PARSE_TIMEOUT );
          if ( ret > 0 )
            ret = strstr( ce_p->av_inf, "ENCRYPTED" )==NULL && strstr( ce_p->av_inf, "NO-DATA" )==NULL ;
            if ( ret )
             if ( ++ce_channel_num > ce_num )
               break;
      }
    }
  } while ( 0 );

  hdhomerun_device_tuner_lockkey_release(hd);

  if (ret < 0) {
    fprintf(stderr, "communication error sending request to hdhomerun device\n");
  }
  return found_channel;
}

int scan_vchannel( void* device, int vchannel, struct channel_entry_t *ce )
{
  int ret;
  struct hdhomerun_device_t *hd =(struct hdhomerun_device_t *)device;
  if ( hd == NULL ) {
    sage_log(( _LOG_ERROR, 3, "hdhomerun invalid handle." ));
    return -1;
  }

  ce->state = 1;
  ce->ch = vchannel;
  ce->frq = 0;
  ce->av_inf[0] = 0x0;
  char stream_tar[32];
  snprintf( ce->ch_name, sizeof(ce->ch_name), "%d", vchannel );
  snprintf( ce->dev_tuning, sizeof(ce->dev_tuning), "vchan:%d", vchannel );
  snprintf( stream_tar, sizeof(stream_tar), "udp://%s:%u", CHANNE_SCAN_SRC, CHANNEL_SCAN_PORT );
  ret = tune_channel( device, ce->dev_tuning, "", stream_tar );
  if ( ret > 0 )
    ret = parse_avinf( CHANNE_SCAN_SRC, CHANNEL_SCAN_PORT, ce->av_inf, sizeof(ce->av_inf), PARSE_TIMEOUT );
    if ( ret > 0 )
      ret = strstr( ce->av_inf, "ENCRYPTED" )==NULL && strstr( ce->av_inf, "NO-DATA" )==NULL ;
  if ( ret <= 0 ) {
    ce->state = 0;
    return 0;
  }

  return 1;
}

static int _make_channel_entry_buffer( struct channel_entry_t *ce, char *buf, int size )
{
  int pos = 0;
  pos += snprintf( buf+pos, size-pos, "ch:%03d ", ce->ch );
  if ( ce->ch_name[0] )
    pos += snprintf( buf+pos, size-pos, "name:%s ", ce->ch_name );
  if ( ce->src_ip[0] && ce->src_port )
    pos += snprintf( buf+pos, size-pos, "ip:%s port:%d ", ce->src_ip, ce->src_port);
  if ( ce->epg_id[0] )
    pos += snprintf( buf+pos, size-pos, "epg:%s ", ce->epg_id );
  if ( ce->dev_name[0] )
    pos += snprintf( buf+pos, size-pos, "dev:%s ", ce->dev_name );
  if ( ce->dev_tuning[0] )
    pos += snprintf( buf+pos, size-pos, "tune:%s ", ce->dev_tuning );
  if ( ce->av_inf[0] )
    pos += snprintf( buf+pos, size-pos, "av:\"%s\" ", ce->av_inf );
  pos += snprintf( buf+pos, size-pos, "\n" );
  return pos;
}

static int _save_channel_entry( char* file_name, struct channel_entry_t *ce, int num )
{
  int i;
  char buf[2048];
  FILE *fp;
  fp = fopen( file_name, "w" );
  if ( fp == NULL ) {
    //printf( "Can't open file %s to save channel table, errno:%d\n", file_name, errno );
    return -1;
  }
  fputs( "#Google sagetv channel table ver 1.0., maxium 2048 bytes per line\n", fp );
  fprintf( fp, "total_channel:%d\n", num );
  for ( i = 0; i<num; i++ ) {
    _make_channel_entry_buffer( ce, buf, sizeof(buf) );
    fputs( buf, fp );
    ce++;
  }
  fclose( fp );
  return 1;
}

int main( int argc, char* argv[] )
{
  int  i, ret = 0 ;
  int tuner_count = 0;
  struct hdhr_tuner_t ht[16];

  ret = discover_device( ht, 16 );
  printf( "found tuners:%d\n", ret );
  if ( ret > 0 ) {
    for ( i = 0; i<ret; i++ ) {
      //if a unit shares a source input in a device, copy data.
      if ( i> 0 && tuner_input_sharing( &ht[i-1], &ht[i] ) ) {
        ht[i].cc_tuner = ht[i-1].cc_tuner;
        strncpy( ht[i].model, ht[i-1].model, sizeof(ht[i].model) );
      } else
        get_dev_model( &ht[i] );

      printf( "%d tuner:%s ip:%s type:%d cc:%d model:%s\n", i, ht[i].name, ht[i].ip, ht[i].type, ht[i].cc_tuner, ht[i].model );
    }
    tuner_count = ret;
  }

  // test channel scan
  if ( 0 ) {
    time_t t0 = time( NULL );
    struct channel_entry_t ce[400];
    int channel_num = 0;
    //channel_num = scan_all( "101007FD-0", ce, 400 );
    for ( i = 60; i<=70; i++ ) {
      ret = scan_channel( "101007FD-1", i, ce, channel_num, 400 );
      if ( ret < 0 || sigabort_flag )
        break;
      printf( "find channe:%d\n", ret );
      channel_num += ret;
    }
    printf( "time:%ld\n", time( NULL) - t0 );
   _save_channel_entry( "channel-scan.txt", ce, channel_num );
  }

  /*
  //test vchannel scan
  if ( 1 ) {
    struct hdhr_tuner_t *cc_ht = NULL;
    for ( i = 0; i<tuner_count; i++ ) {
      if ( ht[i].cc_tuner ) {
        cc_ht = &ht[i];
        break;
      }
    }


    if (  cc_ht != NULL ) {
      time_t t0 = time( NULL );
      struct vchan_tbl_t * vt = create_vchan_tbl( cc_ht );
      ret = get_vchannel_list( vt );
      if ( ret > 0 ) {
        int n;
        int channel_num = 0;
        struct channel_list_t *cl = create_channel_list( ret );
        for ( n = 1; n<vt->channel_num && channel_num < 500 ; n++ ) {
          printf( "TRACE %d %s\n", n, vt->vchan[n].guide_name );
          ret = scan_vchannel( vt, n, cl );
          if ( ret > 0 ) {
            struct channel_entry_t *ce_p = &cl->ce[channel_num];
            snprintf( ce_p->dev_name, sizeof(ce_p->dev_name), "HDHR.%s", device, sizeof(ce_p->dev_name) );
            channel_num++;
          }
          printf( "TRACE channel %d, %d\n", channel_num, n );
        }
         _save_channel_entry( "channel-scan.txt", cl );
      }
      release_vchan_tbl( vt );
      printf( "time:%ld\n", time( NULL) - t0 );
    }
  }
  */

  //test tune
  if ( 1 ) {
    //printf( "tuning %s \n", device[i] );
    char *dev_name = "1311A273-0"; //"101007FD-1";
    //ret = tune_channel( dev_name, "map:us-cable|auto:68", "343", "udp://226.0.0.1:4096" );
    ret = tune_channel( dev_name, "vchan:600", "", "udp://226.0.0.1:4096" );
    printf( "hit enter to stop\n" );
    getchar();
    ret = stop_channel( dev_name );
  }

  return ret;
}
#endif
