⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 device_new.c

📁 <B>SMSC USB2.0 Flash硬盘驱动源码</B>
💻 C
📖 第 1 页 / 共 5 页
字号:

  TRACE1(38, dev, 0, "dev_cpex(msg:%04X)", message_rd_id(msgp));
  rqstp = (t_usb_rqst *)message_rd_arg(msgp);
  g_wtmp = rqstp->wLengthHi;
  g_wtmp *= 256;
  g_wtmp += (uint16)rqstp->wLengthLo;
  switch (message_rd_id(msgp))
  {
    case k_dsd_usb_get_descriptor:
      _nvram_insert_vidpid = k_false;
      _nvram_ix = 0;
      _nvram_sz = 0;
      TRACE3(39, dev, 0, "wLengthHi:%02X wLengthLo:%02X wtmp:%d", rqstp->wLengthHi, rqstp->wLengthLo, g_wtmp);
      switch (rqstp->wValueHi)
      {
        case k_usb_dscr_typ_device:
          TRACE0(40, dev, 0, "RQ_GET_DESCRIPTOR: device");
          // tell the data pump where to find it and how much there is
          if (sie_is_high_speed())
          {
            // eeprom vid/pid => if eeprom is valid, insert vidpid
            _nvram_insert_vidpid = _nvram_data_valid;
            _payload_source((_serial_number_valid?(&g_hs_dev_dscr_w_ser):(&g_hs_dev_dscr)), _min(g_hs_dev_dscr[0], g_wtmp));
          }
          else
          {
            // eeprom vid/pid => if eeprom is valid, insert vidpid
            _nvram_insert_vidpid = _nvram_data_valid;
            _payload_source((_serial_number_valid?(&g_fs_dev_dscr_w_ser):(&g_fs_dev_dscr)), _min(g_fs_dev_dscr[0], g_wtmp));
          }
          break;

        case k_usb_dscr_typ_devqual:
          TRACE0(41, dev, 0, "RQ_GET_DESCRIPTOR: devqual");
          // tell the data pump where to find it and how much there is
          if (sie_is_high_speed())
          {
            _payload_source(&g_fs_devqual_dscr, _min(g_fs_devqual_dscr[0], g_wtmp));
          }
          else
          {
            _payload_source(&g_hs_devqual_dscr, _min(g_hs_devqual_dscr[0], g_wtmp));
          }
          break;

        case k_usb_dscr_typ_config:
          TRACE0(42, dev, 0, "RQ_GET_DESCRIPTOR: configuration");
          // make sure it is in the supported range
          if (rqstp->wValueLo > k_dev_max_configuration)
            return k_error;
          // tell the data pump where to find it and how much there is
          if (sie_is_high_speed())
          {
            _payload_source(&g_hs_cfg_dscr, _min(g_hs_cfg_dscr[2], g_wtmp));
          }
          else
          {
            _payload_source(&g_fs_cfg_dscr, _min(g_fs_cfg_dscr[2], g_wtmp));
          }
          break;

        case k_usb_dscr_typ_osconfig:
          TRACE0(43, dev, 0, "RQ_GET_DESCRIPTOR: other speed configuration");
          // make sure it is in the supported range
          if (rqstp->wValueLo > k_dev_max_configuration)
            return k_error;
          // tell the data pump where to find it and how much there is
          if (sie_is_high_speed())
          {
            _payload_source( &g_fs_oscfg_dscr, _min(g_fs_oscfg_dscr[2], g_wtmp));
          }
          else
          {
            _payload_source(&g_hs_oscfg_dscr, _min(g_hs_oscfg_dscr[2], g_wtmp));
          }
          break;

        case k_usb_dscr_typ_string:
          TRACE0(44, dev, 0, "RQ_GET_DESCRIPTOR: string");
          // make sure it is in the supported range
          if (rqstp->wValueLo >= k_dev_max_string)
            return k_error;
          #ifdef k_support_nvram
          // tell the data pump where to find it and how much there is
          // grab string from rom, unless its asking for the serial number...
          if (_nvram_data_valid)
          {
            switch (rqstp->wValueLo)
            {
              case k_dev_idx_str_dscr_lng:
                TRACE0(45, dev, 0, "source: eeprom Language ID String descriptor");
                _nvram_ix  = k_ix_lng;  // data only (same semantics as _source_eeprom_raw=k_false)
                _nvram_sz  = nvram_read(k_ix_lng);
                break;

              case k_dev_idx_str_dscr_mfg:
                TRACE0(46, dev, 0, "source: eeprom Manufacturer ID String descriptor");
                _nvram_ix  = k_ix_mfr;  // data only (same semantics as _source_eeprom_raw=k_false)
                _nvram_sz  = nvram_read(k_ix_mfr);
                break;

              case k_dev_idx_str_dscr_prd:
                TRACE0(47, dev, 0, "source: eeprom Product ID String descriptor");
                _nvram_ix  = k_ix_prd;  // data only (same semantics as _source_eeprom_raw=k_false)
                _nvram_sz  = nvram_read(k_ix_prd);
                break;

              case k_dev_idx_str_dscr_ser:
                // ... in which case, extract it from the eeprom
                if (_serial_number_valid)
                {
                  TRACE0(48, dev, 0, "source: eeprom Serial Number String descriptor");
                  _nvram_ix  = k_ix_ser;  // data only (same semantics as _source_eeprom_raw=k_false)
                  _nvram_sz  = nvram_read(k_ix_ser);
                }
                else
                {
                  TRACE0(49, dev, 0, "warning:  source, eeprom Serial Number String, not valid.  no serial # reported");
                  return k_error;
                }
                break;
              default:
                TRACE1(50, dev, 0, "warning:  no string descriptor at index %d", rqstp->wValueLo);
                return k_error;
            }
            // send it along
            // _payload_source(NULL, _min(eeprom_read(_nvram_ix), g_wtmp));
            _payload_source(NULL, _min(_nvram_sz, g_wtmp));
          }
          else
          {
            if (rqstp->wValueLo != k_dev_idx_str_dscr_ser)
            {
              TRACE0(51, dev, 0, "source:  default string descriptor");
              _payload_source(g_str_dscr[rqstp->wValueLo], _min(*((uint8 *)g_str_dscr[rqstp->wValueLo]), g_wtmp));
            }
            else
            {
              // cannot happen
              TRACE1(52, dev, 0, "warning:  no string descriptor at index %d", rqstp->wValueLo);
              return k_error;
            }
          }
          #else
          TRACE0(53, dev, 0, "source:  default string descriptor (eeprom support disabled)");
          _payload_source(g_str_dscr[rqstp->wValueLo], _min(*((uint8 *)g_str_dscr[rqstp->wValueLo]), g_wtmp));
          #endif
          break;

        default:
          return k_error;
      }
      return k_success;

    case k_hsd_usb_set_configuration:
      TRACE0(54, dev, 0, "RQ_SET_CONFIGURATION");
      if ((uint8)message_rd_arg(msgp))  // unconfigured -> configured
        dev_power_up();
      else
        dev_power_dn();
      dev_wr_most_recent_config(sie_rd_configuration());
      return k_success;

      // vendor specific requests
    case k_hci_dfu_detach:
      trace0(0, dfu, 0, "k_hci_dfu_detach");
      return dfu_cpex(msgp);

    case k_hvd_wr_eerom:
      TRACE1(55, dev, 0, "k_hvd_wr_eerom - length:%d", g_wtmp);
      _nvram_ix = 0;
      _nvram_sz = 256;
      _payload_sink(NULL, _min(256, g_wtmp));
      return k_success;

    case k_dvd_rd_eerom:
      TRACE1(56, dev, 0, "k_hvd_rd_eerom - length:%d", g_wtmp);
      _nvram_ix = 0;
      _nvram_sz = 256;
      _payload_source(NULL, _min(256, g_wtmp));
      return k_success;

    case k_dvd_inq_devid:
      TRACE0(57, dev, 0, "k_dvd_inq_devid");
      _payload_source(_devid, sizeof(_devid));
      return k_success;

      // requests from the usb protocol engine
    case k_msg_source_payload:
      // load some application specific data into a packet buffer
      // return k_in_progress if app expects to be supply at least one more packet's worth of data
      // return k_finished otherwise
      pnr = *(uint8 *)message_rd_arg(msgp);
      pktsz = _min(g_data_len, k_maxpktsz);
      g_data_len -= pktsz;
      TRACE2(58, dev, 0, "k_msg_source_payload - pnr:%d pktsz:%d", pnr, pktsz);
      // NULL addr means read non-volitile memory location like eeprom, flashed config info or hard-coded bytes
      #ifdef k_support_nvram
      if (NULL == g_source_addr)
      {
        nvram_source_payload(pnr, pktsz) ;
      }
      else
      #endif
      {
        // write the default data
        mmu_wr_pkt(0, pnr, g_source_addr, pktsz);

        #ifdef k_support_nvram
        if ( _nvram_insert_vidpid )
        {
          // overwrite the default data with eeprom vid-pid
          mcu_begin_critical_section();
          _mcu_register_wr(x_sram_addr_lo, (k_pkt_addrlo[pnr]+k_ix_dev_vid_lo) );
          _mcu_register_wr(x_sram_addr_hi, k_pkt_addrhi[pnr]);

          _mcu_register_wr(x_sram_data, nvram_read(k_ix_vid_lo));
          _mcu_register_wr(x_sram_data, nvram_read(k_ix_vid_hi));
          _mcu_register_wr(x_sram_data, nvram_read(k_ix_pid_lo));
          _mcu_register_wr(x_sram_data, nvram_read(k_ix_pid_hi));

          _nvram_insert_vidpid = k_false;
          mcu_end_critical_section();
        }
        #endif
        g_source_addr += pktsz;
      }
      return g_data_len ? k_in_progress : k_finished;

    case k_msg_sink_payload:
      // unload data from a packet buffer and do something application specific with it
      // return k_in_progress if app can process this request
      // return k_finished otherwise
      pnr = *(uint8 *)message_rd_arg(msgp);
      TRACE1(59, dev, 0, "and the packet number is:%d", pnr);
      pktsz = _min(g_data_len, k_maxpktsz);
      g_data_len -= pktsz;
      #ifdef k_support_nvram

      // NULL means write the eeprom
      if (NULL == g_sink_addr)
      {
        nvram_sink_payload(pnr, pktsz) ;
      }
      else
      #endif
      {
        mmu_rd_pkt(pnr, pktsz, g_sink_addr);
        g_sink_addr += pktsz;
      }
      return g_data_len ? k_in_progress : k_finished;

    default:
      return k_error;
  }
  return k_error;
}

//------------------------------------------------------------------------------
// Declaration:
//   t_result dev_intr(uint8 intr);
//
// Purpose:
//   Handle interrupts.
//
// Arguments:
//   intr - the interrupt that occurred. It is a number, not a bitmask.
//
// Return:
//   k_ignored - causes default processing within the kernel isr
//   k_success - prevents default processing within the kernel isr
//
// Note:
//   This function is called from the kernel isrs.  Therefore it executes at
//   interrupt level, not foreground level.
//
//   This function uses register bank 1 (as do the kernel's isrs) so you cannot
//   call any function that is not wrapped by the #pragma NOAREGS.
//   Only functions wrapped by this #pragma are callable from the isrs
//   (except this one, of course, because it explicitly uses register bank 1...)
//
//   Do NOT yield from this routine.  It is NOT part of any thread.  It does
//   not execute in an any thread's context.  Yielding from within this function
//   will cause your firmware to flounder, panic, flail, and eventually expire.
//
// Since:
//   fmc-1.0
//------------------------------------------------------------------------------
extern t_isr_fragment _hpbot_thread_entry;
t_result dev_intr(uint8 intr) reentrant using 1
{
  t_result rslt;

  TRACE1(60, dev, 1, "-(dev_intr(%d))", intr);
  _stack_check();

  // give first crack at it to the high priority interrupt chain
  rslt = k_ignored;
  if (_hpbot_thread_entry)
    rslt = (*_hpbot_thread_entry)(intr);
  if (rslt != k_ignored)
    return rslt;

  // high priority interupt chain didn't process it, so synchronize the foreground
  switch (intr)
  {
    case k_irq_ramwr_a:           // external0
      // current xfer TO sram buffer A has completed
      TRACE0(61, dev, 1, "--(k_irq_ramwr_a)");
      thread_set_sync(g_ix_dev_thread, kbm_sync_usbrx);
      return k_ignored;

    case k_irq_ramwr_b:           // external0
      // current xfer TO sram buffer B has completed
      TRACE0(62, dev, 1, "--(k_irq_ramwr_b)");
      thread_set_sync(g_ix_dev_thread, kbm_sync_usbrx);
      return k_ignored;

    case k_irq_ramrd_a:           // external0
      // current xfer FROM sram buffer A has completed
      TRACE0(63, dev, 1, "--(k_irq_ramrd_a)");
      thread_set_sync(g_ix_dev_thread, kbm_sync_usbtx);
      return k_ignored;

    case k_irq_ramrd_b:           // external0
      // current xfer FROM sram buffer B has completed
      TRACE0(64, dev, 1, "--(k_irq_ramrd_b)");
      thread_set_sync(g_ix_dev_thread, kbm_sync_usbtx);
      return k_ignored;

    case k_irq_nak2rx:            // external5

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -