GNU ARM Eclipse:如何模拟引脚输入?

GNU ARM Eclipse: how to simulate pin input?

我想将正弦波数据传递到引脚(任何可能的引脚),以便我的程序在模拟器中 运行 时能够读取它。

我如何以 (time:value) 的形式传递数据或仅传递一个函数 float generatorForPinX(int time); 作为信号发生器进入 GNU ARM Eclipse(我使用 QEMU,但如果任何其他模拟器是需要我愿意迁移)板仿真器?

这些说明用于模拟 Olimex STM32 P103 开发套件。

下载并构建

首先下载并构建 Qemu STM32,其中包括用于在 STM32 上模拟 ADC 外设的补丁:

wget https://github.com/beckus/qemu_stm32/archive/stm32.tar.gz
tar xf stm32.tar.gz
cd qemu_stm32-stm32
./configure --target-list="arm-softmmu"
make
cd ..

如果配置步骤失败,则安装缺少的要求。有关详细信息,请参阅自述文件。

然后下载 Olimex STM32 P103 Development Kit Demos:

wget https://github.com/beckus/stm32_p103_demos/archive/master.tar.gz
tar xf master.tar.gz

stm32_p103_demos-master/demos/adc_single/main.c 中查找使用 ADC 的示例程序。

运行 演示应用程序

要构建和 运行 adc_single 演示:

cd stm32_p103_demos-master
QEMU_ARM_DIR=../qemu_stm32-stm32/arm-softmmu/ make adc_single_QEMURUN_TEL
(from another terminal) telnet localhost 7777

UART2 连接到端口 7777 上的 telnet 服务器,您应该可以看到输出。有关如何构建和 运行 演示应用程序的更多信息,请参阅自述文件。

查看 source for the adc_single demo application,它有 3 种不同的模式:

  • 模式 1(默认)将从 ADC 通道 16 上的温度传感器读取
  • 模式 2 将从 ADC 通道 16 读取 Vdd 值
  • 模式 3 将从 ADC 通道 8 读取。

可以使用按钮选择模式,但由于我们使用 QEMU 模拟硬件,因此该按钮不可用。我通过更改 int mode = 1; 值并重新编译程序来在模式之间切换。

ADC 仿真

QEMU 用来模拟每个 ADC 通道的方法可以在 hw/arm/stm32_adc.c 中的 stm32_adc_start_conv 函数中查看:

static void stm32_adc_start_conv(Stm32Adc *s)
{
    uint64_t curr_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
    int channel_number=stm32_ADC_get_channel_number(s,1);
    // Write result of conversion
    if(channel_number==16){
        s->Vdda=rand()%(1200+1) + 2400; //Vdda belongs to the interval [2400 3600] mv
        s->Vref=rand()%(s->Vdda-2400+1) + 2400; //Vref belongs to the interval [2400 Vdda] mv
        s->ADC_DR= s->Vdda - s->Vref; 
    }
    else if(channel_number==17){
        s->ADC_DR= (s->Vref=rand()%(s->Vdda-2400+1) + 2400); //Vref [2400 Vdda] mv
    }
    else{
        s->ADC_DR=((int)(1024.*(sin(2*M_PI*qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL)/1e9)+1.))&0xfff);
    }
    s->ADC_SR&=~ADC_SR_EOC;  // jmf : indicates ongoing conversion
    // calls conv_complete when expires      
    timer_mod(s->conv_timer,  curr_time + stm32_ADC_get_nbr_cycle_per_sample(s,channel_number)); 
}

如您所见,ADC 通道 16 将模拟随机 Vdd 输入,ADC 通道 17 将模拟随机温度输入,所有其他通道将遵循从 0 到 2048 的正弦波。这是一个图表从所有 3 种模式返回的 ADC 值:

如果您想让 ADC 通道使用不同的仿真模式,您可以修改 stm32_adc_start_conv 并按照上述步骤重建 QEMU。