Beispiel #1
0
s32 SEQ_TERMINAL_PrintSdCardInfo(void *_output_function)
{
  void (*out)(char *format, ...) = _output_function;

  FRESULT res;
  FILINFO fno;
  DIR dir;
  char *fn;
  char str_buffer[128];

  MUTEX_MIDIOUT_TAKE;

  out("SD Card Informations\n");
  out("====================\n");

#if !defined(MIOS32_FAMILY_EMULATION)
  // this yield ensures, that Debug Messages are sent before we continue the execution
  // Since MIOS Studio displays the time at which the messages arrived, this allows
  // us to measure the delay of following operations
  taskYIELD();

  MUTEX_SDCARD_TAKE;
  SEQ_FILE_PrintSDCardInfos();
  MUTEX_SDCARD_GIVE;
#endif

  out("\n");
  out("Reading Root Directory\n");
  out("======================\n");

  taskYIELD();

  if( !SEQ_FILE_SDCardAvailable() ) {
    sprintf(str_buffer, "not connected");
  } else if( !SEQ_FILE_VolumeAvailable() ) {
    sprintf(str_buffer, "Invalid FAT");
  } else {
    out("Retrieving SD Card informations - please wait!\n");
    MUTEX_MIDIOUT_GIVE;
    MUTEX_SDCARD_TAKE;
    SEQ_FILE_UpdateFreeBytes();
    MUTEX_SDCARD_GIVE;
    MUTEX_MIDIOUT_TAKE;

    sprintf(str_buffer, "'%s': %u of %u MB free", 
	    SEQ_FILE_VolumeLabel(),
	    (unsigned int)(SEQ_FILE_VolumeBytesFree()/1000000),
	    (unsigned int)(SEQ_FILE_VolumeBytesTotal()/1000000));
  }
  out("SD Card: %s\n", str_buffer);

  taskYIELD();

#if _USE_LFN
  static char lfn[_MAX_LFN * (_DF1S ? 2 : 1) + 1];
  fno.lfname = lfn;
  fno.lfsize = sizeof(lfn);
#endif

  MUTEX_SDCARD_TAKE;
  if( (res=f_opendir(&dir, "/")) != FR_OK ) {
    out("Failed to open root directory - error status: %d\n", res);
  } else {
    while( (f_readdir(&dir, &fno) == FR_OK) && fno.fname[0] ) {
#if _USE_LFN
      fn = *fno.lfname ? fno.lfname : fno.fname;
#else
      fn = fno.fname;
#endif
      char date[10];
      ShowFatDate(fno.fdate,(char*)&date);
      char time[12];
      ShowFatTime(fno.ftime,(char*)&time);
      out("[%s%s%s%s%s%s%s] %s  %s   %s %u %s\n",
		(fno.fattrib & AM_RDO ) ? "r" : ".",
		(fno.fattrib & AM_HID ) ? "h" : ".",
		(fno.fattrib & AM_SYS ) ? "s" : ".",
		(fno.fattrib & AM_VOL ) ? "v" : ".",
		(fno.fattrib & AM_LFN ) ? "l" : ".",
		(fno.fattrib & AM_DIR ) ? "d" : ".",
		(fno.fattrib & AM_ARC ) ? "a" : ".",
		date,time,
		(fno.fattrib & AM_DIR) ? "<DIR>" : " ",
		fno.fsize,fn);
    }
  }
  MUTEX_SDCARD_GIVE;

  taskYIELD();

  out("\n");
  out("Checking SD Card at application layer\n");
  out("=====================================\n");

  out("Current session: /SESSIONS/%s\n", seq_file_session_name);

  {
    u8 bank;
    for(bank=0; bank<SEQ_FILE_B_NUM_BANKS; ++bank) {
      int num_patterns = SEQ_FILE_B_NumPatterns(bank);
      if( num_patterns )
	out("File /SESSIONS/%s/MBSEQ_B%d.V4: valid (%d patterns)\n", seq_file_session_name, bank+1, num_patterns);
      else
	out("File /SESSIONS/%s/MBSEQ_B%d.V4: doesn't exist\n", seq_file_session_name, bank+1, num_patterns);
    }

    int num_maps = SEQ_FILE_M_NumMaps();
    if( num_maps )
      out("File /SESSIONS/%sMBSEQ_M.V4: valid (%d mixer maps)\n", seq_file_session_name, num_maps);
    else
      out("File /SESSIONS/%s/MBSEQ_M.V4: doesn't exist\n", seq_file_session_name);
    
    int num_songs = SEQ_FILE_S_NumSongs();
    if( num_songs )
      out("File /SESSIONS/%s/MBSEQ_S.V4: valid (%d songs)\n", seq_file_session_name, num_songs);
    else
      out("File /SESSIONS/%s/MBSEQ_S.V4: doesn't exist\n", seq_file_session_name);

    if( SEQ_FILE_G_Valid() )
      out("File /SESSIONS/%s/MBSEQ_G.V4: valid\n", seq_file_session_name);
    else
      out("File /SESSIONS/%s/MBSEQ_G.V4: doesn't exist\n", seq_file_session_name);
    
    if( SEQ_FILE_C_Valid() )
      out("File /SESSIONS/%s/MBSEQ_C.V4: valid\n", seq_file_session_name);
    else
      out("File /SESSIONS/%s/MBSEQ_C.V4: doesn't exist\n", seq_file_session_name);
    
    if( SEQ_FILE_HW_Valid() )
      out("File /SESSIONS/%s/MBSEQ_HW.V4: valid\n", seq_file_session_name);
    else
      out("File /SESSIONS/%s/MBSEQ_HW.V4: doesn't exist or hasn't been re-loaded\n", seq_file_session_name);
  }

  out("done.\n");
  MUTEX_MIDIOUT_GIVE;

  return 0; // no error
}
Beispiel #2
0
/////////////////////////////////////////////////////////////////////////////
// This task is called periodically each second
/////////////////////////////////////////////////////////////////////////////
void SEQ_TASK_Period1S(void)
{
  static s8 wait_boot_ctr = 3; // wait 3 seconds before loading from SD Card - this is to increase the time where the boot screen is print!
  u8 load_sd_content = 0;

  // poll for IIC modules as long as HW config hasn't been locked (read from SD card)
  // TODO: use proper mutex handling here
#ifndef MIOS32_FAMILY_EMULATION
  if( !SEQ_FILE_HW_ConfigLocked() ) {
    MIOS32_IIC_MIDI_ScanInterfaces();
  }
#endif  

  // boot phase of 2 seconds finished?
  if( wait_boot_ctr > 0 ) {
    --wait_boot_ctr;
    if( wait_boot_ctr )
      return;
  }

  // BLM timeout counter
  MIOS32_IRQ_Disable();
  if( seq_blm_timeout_ctr )
    --seq_blm_timeout_ctr;
  MIOS32_IRQ_Enable();

  // check if SD Card connected
  MUTEX_SDCARD_TAKE;

  s32 status = FILE_CheckSDCard();

  if( status == 1 ) {
    if( wait_boot_ctr != 0 ) { // don't print message if we just booted
      char str[21];
      sprintf(str, "Label: %s", FILE_VolumeLabel());
#ifndef MBSEQV4L
      SEQ_UI_Msg(SEQ_UI_MSG_SDCARD, 2000, " SD Card connected", "        :-D");
#endif
      DEBUG_MSG("SD Card connected: %s\n", FILE_VolumeLabel());
    }
    SEQ_FILE_LoadSessionName();
    DEBUG_MSG("Loading session %s\n", seq_file_session_name);
    SEQ_FILE_LoadAllFiles(1);
  } else if( status == 2 ) {
#ifndef MBSEQV4L
    SEQ_UI_Msg(SEQ_UI_MSG_SDCARD, 2000, "SD Card disconnected", "        :-/");
#endif
    DEBUG_MSG("SD Card disconnected\n");
    SEQ_FILE_UnloadAllFiles();
    wait_boot_ctr = -1;
  } else if( status == 3 ) {
    if( !FILE_SDCardAvailable() ) {
#ifndef MBSEQV4L
      SEQ_UI_Msg(SEQ_UI_MSG_SDCARD, 2000, "  No SD Card found  ", "        :-(");
#endif
      DEBUG_MSG("SD Card not found\n");
      SEQ_FILE_HW_LockConfig(); // lock configuration
      wait_boot_ctr = -1;
    } else if( !FILE_VolumeAvailable() ) {
#ifndef MBSEQV4L
      SEQ_UI_Msg(SEQ_UI_MSG_SDCARD, 2000, "!! SD Card Error !!!", "!! Invalid FAT !!!!!");
#endif
      DEBUG_MSG("ERROR: SD Card contains invalid FAT!\n");
      SEQ_FILE_HW_LockConfig(); // lock configuration
      wait_boot_ctr = -1;
    } else {
#ifndef MBSEQV4L
      if( wait_boot_ctr != 0 ) { // don't print message if we just booted
	char str1[30];
	sprintf(str1, "Banks: ....");
	u8 bank;
	for(bank=0; bank<4; ++bank)
	  str1[7+bank] = SEQ_FILE_B_NumPatterns(bank) ? ('1'+bank) : '-';
	char str2[30];
	sprintf(str2, 
		"M:%c S:%c G:%c C:%c%c HW:%c", 
		SEQ_FILE_M_NumMaps() ? '*':'-',
		SEQ_FILE_S_NumSongs() ? '*':'-',
		SEQ_FILE_G_Valid() ? '*':'-',
		SEQ_FILE_C_Valid() ? 'S':'-',
		SEQ_FILE_GC_Valid() ? 'G':'-',
		SEQ_FILE_HW_Valid() ? '*':'-');
	SEQ_UI_Msg(SEQ_UI_MSG_SDCARD, 2000, str1, str2);
      }
#endif

#if MBSEQV4L
      // auto-format
      // check if formatting is required
      if( SEQ_FILE_FormattingRequired() ) {
	strcpy(seq_file_new_session_name, "DEF_V4L");
	DEBUG_MSG("Creating initial session '%s'... this can take some seconds!\n", seq_file_new_session_name);

	if( (status=SEQ_FILE_Format()) < 0 ) {
	  DEBUG_MSG("Failed to create session! (status: %d)\n", status);
	} else {
	  SEQ_FILE_StoreSessionName();
	  DEBUG_MSG("Done!\n");
	}
      }
#endif

      // request to load content of SD card
      load_sd_content = 1;

      // notify that boot finished
      wait_boot_ctr = -1;
    }
  } else if( status < 0 ) {
    wait_boot_ctr = -1;
#ifndef MBSEQV4L
    SEQ_UI_SDCardErrMsg(2000, status);
#endif
    DEBUG_MSG("ERROR: SD Card Error %d (FatFs: D%3d)\n", status, file_dfs_errno);
  }

  // check for format request
  // this is running with low priority, so that LCD is updated in parallel!
  if( seq_ui_format_req ) {
    // note: request should be cleared at the end of this process to avoid double-triggers!
    if( (status = SEQ_FILE_Format()) < 0 ) {
#ifndef MBSEQV4L
      SEQ_UI_SDCardErrMsg(2000, status);
#endif
      DEBUG_MSG("ERROR: SD Card Error %d (FatFs: D%3d)\n", status, file_dfs_errno);
    } else {
#ifndef MBSEQV4L
      SEQ_UI_Msg(SEQ_UI_MSG_USER, 1000, "Files created", "successfully!");
#endif
      DEBUG_MSG("Files created successfully!\n");

      // store session name
      status |= SEQ_FILE_StoreSessionName();
    }

    // request to load content of SD card
    load_sd_content = 1;

    // finally clear request
    seq_ui_format_req = 0;
  }

  // check for backup request
  // this is running with low priority, so that LCD is updated in parallel!
  if( seq_ui_backup_req ) {
    // note: request should be cleared at the end of this process to avoid double-triggers!
    status = SEQ_FILE_CreateBackup();
      
    if( status < 0 ) {
      if( status == FILE_ERR_COPY ) {
#ifndef MBSEQV4L
	SEQ_UI_Msg(SEQ_UI_MSG_USER, 2000, "COPY FAILED!", "ERROR :-(");
#endif
	DEBUG_MSG("ERROR: copy failed!\n");
      } else {
#ifndef MBSEQV4L
	SEQ_UI_SDCardErrMsg(2000, status);
#endif
	DEBUG_MSG("ERROR: SD Card Error %d (FatFs: D%3d)\n", status, file_dfs_errno);
      }
    }
    else {
#ifndef MBSEQV4L
      SEQ_UI_Msg(SEQ_UI_MSG_USER, 1000, "Files copied", "successfully!");
#endif
      DEBUG_MSG("Files copied successfully!\n");

      // store session name
      status |= SEQ_FILE_StoreSessionName();
    }

    // finally clear request
    seq_ui_backup_req = 0;
  }

  // check for save all request
  // this is running with low priority, so that LCD is updated in parallel!
  if( seq_ui_saveall_req ) {
    s32 status = 0;

    // store all patterns
    int group;
    for(group=0; group<SEQ_CORE_NUM_GROUPS; ++group)
      status |= SEQ_FILE_B_PatternWrite(seq_file_session_name, seq_pattern[group].bank, seq_pattern[group].pattern, group, 1);

    // store config (e.g. to store current song/mixermap/pattern numbers
    SEQ_FILE_C_Write(seq_file_session_name);

    // store global config
    SEQ_FILE_GC_Write();

    // store mixer map
    SEQ_MIXER_Save(SEQ_MIXER_NumGet());

    // store session name
    if( status >= 0 )
      status |= SEQ_FILE_StoreSessionName();

    if( status < 0 ) {
#ifndef MBSEQV4L
      SEQ_UI_SDCardErrMsg(2000, status);
#endif
      DEBUG_MSG("ERROR: SD Card Error %d (FatFs: D%3d)\n", status, file_dfs_errno);
    }

    // finally clear request
    seq_ui_saveall_req = 0;
  }

  MUTEX_SDCARD_GIVE;

  // load content of SD card if requested ((re-)connection detected)
  if( load_sd_content && !SEQ_FILE_FormattingRequired() ) {
    // send layout request to MBHP_BLM_SCALAR
    MUTEX_MIDIOUT_TAKE;
    SEQ_BLM_SYSEX_SendRequest(0x00);
    MUTEX_MIDIOUT_GIVE;

    // TODO: should we load the patterns when SD Card has been detected?
    // disadvantage: current edit patterns are destroyed - this could be fatal during a live session if there is a bad contact!

    SEQ_MIXER_Load(SEQ_MIXER_NumGet());
    SEQ_SONG_Load(SEQ_SONG_NumGet());
  }

#ifndef MBSEQV4L
  SEQ_LCD_LOGO_ScreenSaver_Period1S();
#endif
}