2017-06-02 135 views
-1

我想将正弦波数据传递到一个引脚(任何可能的引脚),以便我的程序能够在模拟器中运行时读取它。我怎样才能以(time:value)的形式传递数据,或者只是传递函数float generatorForPinX(int time);作为GNU ARM Eclipse的信号发生器(我使用QEMU,但是如果需要其他模拟器,我愿意迁移)电路板模拟器?GNU ARM Eclipse:如何模拟引脚输入?

+1

你在模拟什么目标?这个用于STM32的QEMU分支包括具有正弦模式的ADC仿真:https://beckus.github.io/qemu_stm32/ – Tim

+0

@Tim:是的,STM32!非常感谢你!请做一个扩展的答案,并附上一个简短的解释,说明如何让可编译和可运行的QEMU STM32项目添加这样的模拟(只需将源文件添加到项目src目录中)? – DuckQueen

回答

2

这些指令用于模拟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通道的Vdd的值16
  • 模式3将从ADC通道8

这些模式可以通过使用按钮来选择的读取的,但由于我们仿效与QEMU硬件,按钮没有t可用。我通过更改int mode = 1;值并重新编译程序来切换模式。

ADC仿真

该QEMU使用来模拟各ADC通道的方法是在stm32_adc_start_conv函数可见在hw/arm/stm32_adc.c

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 value graph

如果你想有一个ADC通道使用不同的仿真模式,可以修改stm32_adc_start_conv和重建QEMU按照上述步骤。