搜索
bottom↓
回复: 38

谁有PWM生成正弦波的程序?

[复制链接]

出0入0汤圆

发表于 2007-1-10 12:27:04 | 显示全部楼层 |阅读模式
帮个忙,谁有PWM生成正弦波的程序?

阿莫论坛20周年了!感谢大家的支持与爱护!!

知道什么是神吗?其实神本来也是人,只不过神做了人做不到的事情 所以才成了神。 (头文字D, 杜汶泽)

出0入0汤圆

发表于 2007-1-11 17:08:17 | 显示全部楼层
这个恐怕永远都不会有。

出0入0汤圆

发表于 2007-1-11 17:19:44 | 显示全部楼层
PWM 加滤波,

出0入0汤圆

 楼主| 发表于 2007-10-29 08:23:01 | 显示全部楼层
这个东西已经搞定了,用于电力线载波控制的,要的人联系我。

出0入0汤圆

发表于 2007-10-29 08:26:18 | 显示全部楼层
晕,这个很简单的,我还做过PWM生成DTMF呢

出0入0汤圆

 楼主| 发表于 2007-10-29 15:53:03 | 显示全部楼层
koy-917 ,你好!
本人也是抄了一把ATMEL的DTMF实例,不知你在频率的精确控制方面有没有碰到问题。

出0入0汤圆

发表于 2007-11-1 13:53:58 | 显示全部楼层
xiaowei0588,你好!
我的邮箱是: yinyan186@163.com
能不能给你产生正弦波的程序给我看一下,非常感谢!
我也参照AVR314里面的指导写了一段,但是,产生的正弦波效果非常差。
还请指导!

出0入0汤圆

发表于 2007-11-1 17:04:42 | 显示全部楼层
我是用PIC18系列的单片机做的,方法是查表,叠加,这个过程中做电小处理,最后的滤波比较重要,我的精度应该还可以,电信能认出来,示波器上和电话产生的比较接近,如果不知道怎么做,可以看看MICROCHIP的方案,他们给了详细的方法

出0入0汤圆

发表于 2007-11-1 17:05:59 | 显示全部楼层
只要你的表的点数够多,载波够快,精度就能提升

出0入0汤圆

 楼主| 发表于 2007-11-2 07:58:33 | 显示全部楼层
/*--------------------------------------------------*/
/*           main.c                                            */
/*           FYQ,2007,01,03                         */
/*           生成正弦波                             */
/*--------------------------------------------------*/
/*                                                  */
/*     AVR系统的处理器为:   ATMega16               */
/*     AVR系统的晶振频率:   7.3728Mhz              */
/*                                                                                                        */
/*--------------------------------------------------*/

/****************************************************

                        程序修改为OC2输出,PD7脚(管脚21)
                                        2007,10,31

****************************************************/



#include "defines.h"
#include <avr/io.h>
#include <inttypes.h>
#include <avr/interrupt.h>
#include <stdlib.h>
#include <stdio.h>
#include <avr/pgmspace.h>
#include <avr/sleep.h>
#include "sin_table.h"
#include "delay.h"

#define DISABLE_TC2        (TCCR1B&=~_BV(CS22))

#define ENABLE_TC2 (TCCR1B|=_BV(CS22))

//  -----------------全局变量-----------------
uint8_t key_value;

uint8_t x_sw=0x00;

uint16_t x_lutext=0;

uint16_t x_lut;

//  x_sw表(8倍):x_sw=ROUND(8*N_sample*f*510/FCK)


void io_init(void)
{
        DDRD=0xFF;
        PORTD=0xFF;

        DDRA=0xC0;                        //        PA0~PA5为输入,PA6~PA7为输出
        PORTA=0x00;                        //        PORTA关上拉       
}

//定义按键输入
void key_init(void)
{
        DDRA=0xFF;
        PORTA=0xFF;//_BV(PA0)|_BV(PA1)|_BV(PA2)|_BV(PA3);
}

void LedOnOff(void)
{
        uint8_t i;
        for(i=0;i<3;i++)
        {
                PORTA^=_BV(PA7);
                delay_nms(500);
        }

}


void tc2_init()
{       
        TIMSK|=_BV(OCIE2);                                                                                //  使能T/C2溢出中断

        TCCR2|=_BV(CS20);                                                                                //        分频:1

        TCCR2|=_BV(COM21)|_BV(COM20);                                                        //        比较匹配时置位OC2计数值为0xFF时清零OC2                                               
       
        TCCR2|=_BV(WGM21)|_BV(WGM20);                                                        //        快速PWM模式

       
}


SIGNAL(SIG_OUTPUT_COMPARE2)
{       
        x_lutext+=x_sw;

        x_lut=(uint8_t)(((x_lutext+4)>>3)&(0x007F));                        //  数据规格化,0x007F=127

        OCR2=pgm_read_byte(&sin_table[x_lut]);                                        //        从flash中取出正弦数据
                                                                                                                        //        更新OCR2
}

//        读键盘
uint8_t read_key(void)
{
                uint8_t key_v;
               
                key_v=(PINA&0x3F);

                return key_v;
}

int main(void)
{       
        io_init();

        tc2_init();
       
        LedOnOff();       

        sei();                                                                                                        //        开总的中断允许

//        set_sleep_mode(SLEEP_MODE_IDLE);

        while(1)
        {  

                key_value=read_key();               

                switch(key_value){
                       
                        case 0x00:        {x_sw=0;DISABLE_TC2;};break;

                        case 0x01:        {x_sw=1;ENABLE_TC2;};break;
                       
                        case 0x02:        {x_sw=2;ENABLE_TC2;};break;

                        case 0x04:        {x_sw=3;ENABLE_TC2;};break;

                        case 0x08:        {x_sw=4;ENABLE_TC2;};break;

                        case 0x10:        {x_sw=5;ENABLE_TC2;};break;

                        case 0x20:        {x_sw=6;ENABLE_TC2;};break;

                        default:        break;
                       
                        }


//                sleep_mode();

        }

        return 0;
}

出0入0汤圆

 楼主| 发表于 2007-11-2 08:01:37 | 显示全部楼层
//
//        正弦表20060104
//

const prog_uchar sin_table[]=
{
        64,         67,         70,         73,         76,         79,         82,         85,                //0
       
        88,         91,         94,         96,         99,         102,        104,        106,        //1
       
        109,        111,        113,        115,        117,        118,        120,        121,        //2
       
        123,        124,        125,        126,        126,        127,        127,        127,        //3
       
        127,        127,        127,        127,        126,        126,        125,        124,        //4
       
        123,        121,        120,        118,        117,        115,        113,        111,        //5
       
        109,        106,        104,        102,        99,         96,         94,         91,                //6       
       
        88,         85,         82,                79,         76,         73,         70,         67,                //7       
       
        64,         60,         57,         54,         51,         48,         45,         42,                //8
       
        39,         36,         33,         31,         28,         25,         23,         21,                //9
       
        18,         16,         14,                12,         10,         9,          7,          6,                //a
       
        4,          3,          2,          1,          1,           0,          0,          0,                //b       
               
        0,          0,          0,          0,           1,          1,          2,          3,                //c

        4,          6,          7,          9,          10,         12,         14,         16,                //d
       
        18,         21,         23,         25,         28,         31,         33,         36,                //e
       
        39,         42,         45,         48,         51,         54,         57,         60                //f

};

出0入0汤圆

发表于 2007-11-2 14:26:28 | 显示全部楼层
我也做过DTMF,两个频率的相位都是实时计算的,实验可以拨通。另外产生正弦波就更简单了啊。我做逆变器都搞定,呵呵。SPWM嘛。

出0入0汤圆

发表于 2008-1-9 10:16:40 | 显示全部楼层
上面xiaowei0588的程序中
SIGNAL(SIG_OUTPUT_COMPARE2) 是什么意思?主程序里也没用到!

出0入0汤圆

发表于 2008-1-9 10:18:28 | 显示全部楼层
上面xiaowei0588的程序中
SIGNAL(SIG_OUTPUT_COMPARE2) 是什么意思?主程序里也没用到!

出0入0汤圆

发表于 2010-3-25 16:49:33 | 显示全部楼层
呵呵,厉害!!

请问这个正弦表怎么计算出来的?

出0入0汤圆

发表于 2010-4-4 23:46:21 | 显示全部楼层
DTMF  的程序谁有,能否给我一份,我的邮箱:qaz10126@qq.com

出0入0汤圆

发表于 2010-4-4 23:48:20 | 显示全部楼层
回复【3楼】xiaowei0588
-----------------------------------------------------------------------

有没有PWM生成正弦波的频率可变的程序,有的话请发给我一份,谢谢!!

我的邮箱:qaz10126@qq.com

出0入0汤圆

发表于 2010-4-14 16:07:52 | 显示全部楼层
这个程序我也做出来了,但正弦波的频率改变生成的正弦波的幅值也跟着变,郁闷,谁知道为什么,我载波频率并没有改变啊

出0入0汤圆

发表于 2010-4-14 16:14:24 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-4-14 20:02:08 | 显示全部楼层
// Target : M32
// Crystal: 4.0000Mhz

#include <iom32.h>
#include <ina90.h>

#include "delay.h"
//#include <ioavr.h>                     // Use IAR-AVR library

#define uchar unsigned char
#define uint unsigned int
#define   N     98


// 正弦波样本表
__flash unsigned char auc_sinparam[N] = {
  
    128,136,144,152,160,168,175,183,190,197,204,210,216,222,227,232,
237,241,244,247,250,252,253,254,255,255,254,253,252,250,247,244,
241,237,232,227,222,216,210,204,197,190,183,175,168,160,152,144,
136,128,119,111,103,95,87,80,72,65,58,51,45,39,33,28,
23,18,14,11,8,5,3,2,1,0,0,1,2,3,5,8,
11,14,18,23,28,33,39,45,51,58,65,72,80,87,95,103,
111,119
};

unsigned int  x_sw=1;
unsigned int  indexU=0;  
unsigned int  indexV=N/3;  
unsigned int  indexW=2*N/3;


//timer0溢出中断
#pragma vector=TIMER0_OVF_vect
__interrupt void timer0_ovf_isr(void)
{  
   
    indexU+=x_sw;   
    if(indexU>(N-1))   indexU-=N;   
    OCR0  = auc_sinparam[indexU];
   
    indexV+=x_sw;
    if(indexV>(N-1))   indexV-=N;
    OCR1A = auc_sinparam[indexV];
   
    indexW+=x_sw;
    if(indexW>(N-1))   indexW-=N;
    OCR1B = auc_sinparam[indexW];
}


  
void system_init (void)
{
    //port init
    PORTB=0xf7;   
    DDRB=0xff; //PB3--OC0
   
    PORTD=0xff;//pd0-pd3 pull-up enable for key1-key4
    DDRD=0x30;//PD4--OC1A,PD5--0C1B
   
    //timer0 init   
    TCCR0=0x00;   
    OCR0=0xff; //初始值占空比为0
    TCCR0=0x62;//相位修正  8分频  正向输出  启动定时器
   
    //time1 init
    TCCR1A= 0x00;
    OCR1A = 0xff;//正向输出
    OCR1B = 0xff;//正向输出
    //ICR1  = 0xff;
    TCCR1A= 0xa1;
    TCCR1B= 0x02;//相位修正 8分频   启动定时器
   
    indexU=0;  
    indexV=N/3;  
    indexW=2*N/3;
      
    TIMSK=0x01;//time0 over interrupt
    __enable_interrupt(); //re-enable interrupts
}


void main(void)
{
    uchar tem,key;
    system_init();//系统初始化
    while(1)
    {
        tem=0x0f&PIND;       //读取端口b
        if(tem!=0x0f)   //判断是否有按键按下
        {
          //s_ms(50);   //排除按键抖动和抗干扰
          delay_nms(35);
          key=0x0f&PIND;
          if(key==tem)
          {
            x_sw++;
            if(x_sw==6) x_sw=1;
            if(x_sw==1) //fsin=10hz
            {
              PORTB=(1<<PB6)|(1<<PB5)|(1<<PB4)|(1<<PB2)|(1<<PB1)|(1<<PB0);
              PORTB&=~(1<<PB7);
            }
            if(x_sw==2)//fsin=20hz
            {
              PORTB=(1<<PB7)|(1<<PB5)|(1<<PB4)|(1<<PB2)|(1<<PB1)|(1<<PB0);
              PORTB&=~(1<<PB6);
            }
            if(x_sw==3)//fsin=30hz
            {
              PORTB=(1<<PB7)|(1<<PB6)|(1<<PB4)|(1<<PB2)|(1<<PB1)|(1<<PB0);
              PORTB&=~(1<<PB5);
            }
            if(x_sw==4)//fsin=40hz
            {
              PORTB=(1<<PB7)|(1<<PB6)|(1<<PB5)|(1<<PB2)|(1<<PB1)|(1<<PB0);
              PORTB&=~(1<<PB4);
            }
            if(x_sw==5)//fsin=50hz
            {
              PORTB=(1<<PB7)|(1<<PB6)|(1<<PB5)|(1<<PB4)|(1<<PB1)|(1<<PB0);
              PORTB&=~(1<<PB2);
            }
            //PORTB=0x0f|(key<<4);  //端口D输出按键值
          }
        }
        //speed_switch();//按键调速
    }
}

出0入0汤圆

发表于 2010-4-14 20:05:45 | 显示全部楼层
上面的程序有两个错误:、
1、用示波器看到的正弦波频率不是20hz,40hz,60hz,80hz,100hz,而是10hz,20hz,30hz,40hz,50hz,请问是为什么

2、用示波器观察发现:随正弦波频率增大,正弦波幅值会越来越小,请问是为什么

出0入0汤圆

发表于 2011-5-3 23:01:33 | 显示全部楼层
mark

出0入0汤圆

发表于 2011-5-4 07:40:52 | 显示全部楼层
mark

出0入0汤圆

发表于 2011-5-4 09:35:00 | 显示全部楼层
/*
* WSPR beacon for weak signal  radio transmission
* encodes a WSPR message from call locator and power to a symbol/tone  
* and generates sinewaves with a PWM and software DDS
* Thanks to Andy Talbot for his article The WSPR Coding Process
* generates from a Callsign, Locator, and Power Level a symbol Table
* due to the WSPR protocol
* rund on a Arduino Diecimila or Duemilanove board / Arduino 17
*
* ptt connected to pin10
* vfo for tone modulation connected to pin 11
* tone output PWM connected to pin 3
* DCF-time receiver connected to pin 7

* soft DDS with ATMEGS 168
* Timer2 set to 31373 KHz for interrupt and DDS timebase
*
*
*


* KHM 2009 /  Martin Nawrath
* Kunsthochschule fuer Medien Koeln
* Academy of Media Arts Cologne

*/

#include <avr/pgmspace.h>




#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))





//! Macro that clears all Timer/Counter1 interrupt flags.
#define CLEAR_ALL_TIMER1_INT_FLAGS    (TIFR1 = TIFR1)


const char SyncVec[162] = {
  1,1,0,0,0,0,0,0,1,0,0,0,1,1,1,0,0,0,1,0,0,1,0,1,1,1,1,0,0,0,0,0,0,0,1,0,0,1,0,1,0,0,0,0,0,0,1,0,
  1,1,0,0,1,1,0,1,0,0,0,1,1,0,1,0,0,0,0,1,1,0,1,0,1,0,1,0,1,0,0,1,0,0,1,0,1,1,0,0,0,1,1,0,1,0,1,0,
  0,0,1,0,0,0,0,0,1,0,0,1,0,0,1,1,1,0,1,1,0,0,1,1,0,1,0,0,0,1,1,1,0,0,0,0,0,1,0,1,0,0,1,1,0,0,0,0,
  0,0,0,1,1,0,1,0,1,1,0,0,0,1,1,0,0,0
};

// table of 256 sine values / one sine period / stored in flash memory
PROGMEM  prog_uchar sine256[]  = {
  127,130,133,136,139,143,146,149,152,155,158,161,164,167,170,173,176,178,181,184,187,190,192,195,198,200,203,205,208,210,212,215,217,219,221,223,225,227,229,231,233,234,236,238,239,240,
  242,243,244,245,247,248,249,249,250,251,252,252,253,253,253,254,254,254,254,254,254,254,253,253,253,252,252,251,250,249,249,248,247,245,244,243,242,240,239,238,236,234,233,231,229,227,225,223,
  221,219,217,215,212,210,208,205,203,200,198,195,192,190,187,184,181,178,176,173,170,167,164,161,158,155,152,149,146,143,139,136,133,130,127,124,121,118,115,111,108,105,102,99,96,93,90,87,84,81,78,
  76,73,70,67,64,62,59,56,54,51,49,46,44,42,39,37,35,33,31,29,27,25,23,21,20,18,16,15,14,12,11,10,9,7,6,5,5,4,3,2,2,1,1,1,0,0,0,0,0,0,0,1,1,1,2,2,3,4,5,5,6,7,9,10,11,12,14,15,16,18,20,21,23,25,27,29,31,
  33,35,37,39,42,44,46,49,51,54,56,59,62,64,67,70,73,76,78,81,84,87,90,93,96,99,102,105,108,111,115,118,121,124

};

const unsigned long mt[4] = {
800974,801757,802540,803323 }; // DDS freq table for 1497,8 1499,3 1500,7 1502,2 WSPR tones





int ledPin = 13;                 // LED pin 13
int led2Pin = 8;                 // LED pin 13
int t1Pin = 4;            // test pin interrupt        
int t2Pin = 5;            // test pin main      
int pttPin=10;
int dcfPin=7;
int state=0;


// byte sine[258];            // sinewave Memory Array 8-Bit
byte c[11];                // encoded message
byte sym[170];             // symbol table 162
byte symt[170];            // symbol table temp
char call[] = "DH3JO ";    // default values
char locator[] = "JO30";
byte power = 20;
byte dcfPin_a;
int dcfcnt;
int dcfmin;
int dcfhour;
byte n;
byte f_led;




unsigned long n1;    // encoded callsign
unsigned long m1;    // encodes locator

char cnt1;
unsigned char cc1;
int ii,bb;

// interrupt service variables
volatile boolean f_tone;      // set 1,46 Hz tonespacing time flag
volatile unsigned int tcnt;   // tonespacing timer
volatile unsigned long cnt16u;   // 16us timer
volatile byte icnt;
volatile byte icnt2;
volatile unsigned long phaccu;  // soft DDS phase accu
volatile unsigned long mm;      // soft DDS frequency word
volatile unsigned int sycnt;
volatile unsigned int cpin;








void setup()
{
  pinMode(ledPin, OUTPUT);      // sets the digital pin as output
  pinMode(led2Pin, OUTPUT);
  pinMode(t1Pin, OUTPUT);
  pinMode(t2Pin, OUTPUT);

  pinMode(pttPin, OUTPUT);
  pinMode(dcfPin, INPUT);


  pinMode(11, OUTPUT);   // PWM VFO Control
  pinMode(3, OUTPUT);    // PWM WSPR tone output
  Serial.begin(115200);        // connect to the serial port
  Serial.println("WSPR beacon");


  Setup_timer2();




  //cli();                         // disable interrupts to avoid distortion
  //  cbi (TIMSK0,TOIE0);              // disable Timer0 !!! arduino delay function is off now
  sbi (TIMSK2,TOIE2);              // enable Timer2 Interrupt

  OCR2B=64;
  OCR2A=64;

  mm=402063;



  encode_call();
  Serial.print("call: ");
  Serial.print(call);
  Serial.print(" ");
  Serial.print(n1,HEX);
  Serial.println(" ");


  encode_locator();
  Serial.print("locator: ");
  Serial.print(locator);
  Serial.print(" ");
  Serial.print(m1 << 2,HEX);
  Serial.println(" ");


  for (bb=0;bb<=10;bb++){
    Serial.print(c[bb],HEX);
    Serial.print(",");
  }
  Serial.println("");
  encode_conv();

  Serial.println("");

  for (bb=0;bb<162 ;bb++){
    Serial.print(symt[bb],DEC);
    Serial.print(".");
    if ( (bb+1) %32 == 0) Serial.println("");
  }
  Serial.println("");

  interleave_sync();

  for (bb=0;bb<162 ;bb++){
    Serial.print(sym[bb],DEC);
    Serial.print(".");
    if ( (bb+1) %32 == 0) Serial.println("");
  }
  Serial.println("");

  tcnt=0;
  mm=0;
  dcfmin=-1;

}







void loop()

{


  sycnt =0;
  state=10;
  while(1) {

    ii=dcf_minute();

    if ((ii >= 0) && ( ii % 10 ==0) || (ii-2) % 10 ==0 ){ // every 10 minutes for 4 minutes send
      Serial.println("Wspr Start");
      digitalWrite(pttPin,1);
      tcnt=0;  
      sycnt =0;
      state=5;
    }

    if ((ii >= 0) &&  (ii-4) % 10 ==0 ){ // every 10 minutes 6 for 1 minute without ptt
      Serial.println("Wspr Start without ptt");
      tcnt=0;  
      sycnt =0;
      state=5;
    }

    if (f_tone==1) {
      f_tone=0;
      switch (state){
      case 0:
        break;

      case 5:  // Wspr Start with some delay
        if (sycnt==6) {
          sycnt=0;
          state=10;
         
        }

        break;   

      case 10: // Wspr Run


        bb=sym[sycnt];
        mm=mt[bb];  
        OCR2A=240-(40*bb);  // output symbol as a control voltage to vco

        /*
        Serial.print(sycnt);
         Serial.print(" ");
         Serial.print(bb);
         */
        Serial.print("*");

        if (sycnt >= 162) state = 11;
        break;
      case 11: // Wspr Stop

        digitalWrite(pttPin,0);
        break;
      }
    }


  }
} // loop
//******************************************************************
// timer2 setup
// set prscaler to 1, PWM mode to phase correct PWM,  16000000/510 = 31372.55 Hz clock
void Setup_timer2() {
  
// Timer2 Clock Prescaler to : 1
  sbi (TCCR2B, CS20);
  cbi (TCCR2B, CS21);
  cbi (TCCR2B, CS22);
  
  // Timer2 PWM Mode set to Phase Correct PWM
  cbi (TCCR2A, COM2A0);  // clear Compare Match
  sbi (TCCR2A, COM2A1);
  
  cbi (TCCR2A, COM2B0);  // clear Compare Match
  sbi (TCCR2A, COM2B1);

  sbi (TCCR2A, WGM20);  // Mode 3  / fast PWM
  sbi (TCCR2A, WGM21);
  cbi (TCCR2B, WGM22);
  

}

//******************************************************************
int dcf_minute() {
  int bb;
  int bb2,bb3;
  int rr=-1;
  bb= digitalRead(dcfPin);
  if (bb == 1 && dcfPin_a==0) {
    cpin=0;
    digitalWrite(ledPin,f_led);
    digitalWrite(led2Pin,f_led);
    f_led= !f_led;
  }
  if (bb == 0 && dcfPin_a==1) {
    bb2=0;
    dcfcnt++;

    if (cpin > 30) bb2=1;

    if ( dcfcnt >  15 && dcfcnt < 29) {
      /*
      Serial.print(" S:");
       Serial.print(dcfcnt);
       Serial.print(" ");
       Serial.print(bb2);
       */
      Serial.print(".");

    }

    if ((dcfcnt==22)  && (bb2 == 1))   dcfmin +=1;  
    if ((dcfcnt==23)  && (bb2 == 1))   dcfmin +=2;  
    if ((dcfcnt==24)  && (bb2 == 1))   dcfmin +=4;
    if ((dcfcnt==25)  && (bb2 == 1))   dcfmin +=8;
    if ((dcfcnt==26)  && (bb2 == 1))   dcfmin +=10;
    if ((dcfcnt==27)  && (bb2 == 1))   dcfmin +=20;
    if ((dcfcnt==28)  && (bb2 == 1))   dcfmin +=40;

    if ((dcfcnt==30)  && (bb2 == 1))   dcfhour +=1;  
    if ((dcfcnt==31)  && (bb2 == 1))   dcfhour +=2;  
    if ((dcfcnt==32)  && (bb2 == 1))   dcfhour +=4;
    if ((dcfcnt==33)  && (bb2 == 1))   dcfhour +=8;
    if ((dcfcnt==34)  && (bb2 == 1))   dcfhour +=10;
    if ((dcfcnt==35)  && (bb2 == 1))   dcfhour +=20;


  }

  if (cpin > 300) {
    dcfcnt=0;
    cpin=0;
    rr=dcfmin;
    Serial.print("DCF Time:");
    Serial.print(dcfhour);
    Serial.print(":");
    Serial.println(dcfmin);
    dcfmin=0;
    dcfhour=0;

  }
  dcfPin_a=bb;
  return(rr);
}


//******************************************************************
void encode() {
  encode_call();
  encode_locator();
  encode_conv();
  interleave_sync();
};
//******************************************************************
// normalize characters 0..9 A..Z Space in order 0..36
char chr_normf(char bc ) {
  char cc=36;
  if (bc >= '0' && bc <= '9') cc=bc-'0';
  if (bc >= 'A' && bc <= 'Z') cc=bc-'A'+10;
  if (bc == ' ' ) cc=36;

  return(cc);
}

//******************************************************************
void encode_call(){
  unsigned long t1;

  // coding of callsign
  n1=chr_normf(call[0]);
  n1=n1*36+chr_normf(call[1]);
  n1=n1*10+chr_normf(call[2]);
  n1=n1*27+chr_normf(call[3])-10;
  n1=n1*27+chr_normf(call[4])-10;
  n1=n1*27+chr_normf(call[5])-10;

  // merge coded callsign into message array c[]
  t1=n1;
  c[0]= t1 >> 20;
  t1=n1;
  c[1]= t1 >> 12;
  t1=n1;
  c[2]= t1 >> 4;
  t1=n1;
  c[3]= t1 << 4;
}

//******************************************************************
void encode_locator(){

  unsigned long t1;
  // coding of locator
  m1=179-10*(chr_normf(locator[0])-10)-chr_normf(locator[2]);
  m1=m1*180+10*(chr_normf(locator[1])-10)+chr_normf(locator[3]);
  m1=m1*128+power+64;

  // merge coded locator and power into message array c[]
  t1=m1;
  c[3]= c[3] + ( 0x0f & t1 >> 18);
  t1=m1;
  c[4]= t1 >> 10;
  t1=m1;
  c[5]= t1 >> 2;
  t1=m1;
  c[6]= t1 << 6;

}
//******************************************************************
// convolutional encoding of message array c[] into a 162 bit stream
void encode_conv(){
  int bc=0;
  int cnt=0;
  int cc;
  unsigned long sh1=0;

  cc=c[0];

  for (int i=0; i < 81;i++) {
    if (i % 8 == 0 ) {
      cc=c[bc];
      bc++;
    }
    if (cc & 0x80) sh1=sh1 | 1;

    symt[cnt++]=parity(sh1 & 0xF2D05351);
    symt[cnt++]=parity(sh1 & 0xE4613C47);

    cc=cc << 1;
    sh1=sh1 << 1;
  }

}

//******************************************************************
byte parity(unsigned long li)
{
  byte po = 0;
  while(li != 0)
  {
    po++;
    li&= (li-1);
  }
  return (po & 1);
}
//******************************************************************
// interleave reorder the 162 data bits and and merge table with the sync vector
void interleave_sync(){
  int ii,ij,b2,bis,ip;
  ip=0;

  for (ii=0;ii<=255;ii++) {
    bis=1;
    ij=0;
    for (b2=0;b2 < 8 ;b2++) {
      if (ii & bis) ij= ij | (0x80 >> b2);
      bis=bis << 1;
    }
    if (ij < 162 ) {
      sym[ij]= SyncVec[ij] +2*symt[ip];
      ip++;
    }
  }
}



//******************************************************************
// Timer2 Interrupt Service at 31372,550 KHz = 32uSec
// this is the timebase REFCLOCK for the DDS generator
// FOUT = (M (REFCLK)) / (2 exp 32)
// runtime : 8 microseconds ( inclusive push and pop)
ISR(TIMER2_OVF_vect) {

  sbi(PORTD,4);       // set PORTD,4 high to observe timing with a oscope
  //  cnt16u++;
  if (tcnt++ >= 21417) {
    tcnt=0;          // set tone spacing flag at 1,4648 Hz
    f_tone=1;
    sycnt++;
  }

  phaccu=phaccu+mm;   // soft DDS phase accu with 24 bits
  icnt=phaccu >> 16;  // upper 8 bits for pwm modulator
  OCR2B=sine256[icnt];     // send phase state to PWM
  if(icnt2++ == 0) cpin++;


  cbi(PORTD,4);      // set PORTD,4




}

出0入0汤圆

发表于 2011-5-5 18:56:10 | 显示全部楼层
回复【3楼】xiaowei0588  
-----------------------------------------------------------------------
807698017@qq.com 谢谢啊 给我发一份PWM正弦波的资料吧

出0入0汤圆

发表于 2012-5-11 08:29:31 | 显示全部楼层
MARK 3Q ~~~

出0入0汤圆

发表于 2012-5-11 08:41:56 | 显示全部楼层
哦。。原来你们在说SPWM

出0入0汤圆

发表于 2012-5-11 09:31:05 | 显示全部楼层
mark SPWM!

出0入0汤圆

发表于 2012-7-8 20:53:05 | 显示全部楼层
mark 感觉这方面的资料比较少呀。还得慢慢摸索

出0入0汤圆

发表于 2012-10-5 16:19:45 | 显示全部楼层
xiaowei0588 发表于 2007-10-29 08:23
这个东西已经搞定了,用于电力线载波控制的,要的人联系我。

我现在也在搞这个PWM,不知道能不能跟我一些,让我参考!谢谢!我的邮箱850830252@qq.com

出0入0汤圆

发表于 2012-10-5 20:58:16 | 显示全部楼层
mark

出0入0汤圆

发表于 2013-6-2 02:13:26 | 显示全部楼层
mark

出0入0汤圆

发表于 2013-6-2 08:57:13 | 显示全部楼层
mark

出10入113汤圆

发表于 2013-6-2 09:13:57 | 显示全部楼层
查表是最快的

出0入0汤圆

发表于 2013-6-2 09:59:15 | 显示全部楼层
最近怎么老看见挖坟的?

出0入0汤圆

发表于 2013-6-3 07:43:58 | 显示全部楼层
我建议看书!!!!!!!!

出0入0汤圆

发表于 2014-8-13 17:51:35 | 显示全部楼层
koy-917 发表于 2007-10-29 08:26
晕,这个很简单的,我还做过PWM生成DTMF呢

您好 我想请问您关于PWM 输出 DTMF的问题 我现在手上有个项目 我是新人 对于这个问题 我有几个疑惑:
1、目前stm32F4xx的TIME1 最高可以达到168Mhz的时钟,那么我想用这个定时器输出亚音(67Hz 到 245.1Hz )这样的低频 但是输出来幅值很低,不同的频率会有不同的幅值,我怎么才能提高幅值? 目前项目有点急 请您帮助一下? 我的qq是296073773 如果帮我我会好好答谢

出0入0汤圆

发表于 2014-8-13 17:53:52 | 显示全部楼层
koy-917 发表于 2007-10-29 08:26
晕,这个很简单的,我还做过PWM生成DTMF呢

您好 我想请问您关于PWM 输出 DTMF的问题 我现在手上有个项目 我是新人 对于这个问题 我有几个疑惑:
1、目前stm32F4xx的TIME1 最高可以达到168Mhz的时钟,那么我想用这个定时器输出亚音(67Hz 到 245.1Hz )这样的低频 但是输出来幅值很低,不同的频率会有不同的幅值,我怎么才能提高幅值? 目前项目有点急 请您帮助一下? 我的qq是296073773 如果帮我我会好好答谢

出0入0汤圆

发表于 2014-8-13 18:06:05 | 显示全部楼层
qaz10126 发表于 2010-4-14 20:05
上面的程序有两个错误:、
1、用示波器看到的正弦波频率不是20hz,40hz,60hz,80hz,100hz,而是10hz,20hz,30hz ...

师哥 请问这个问题你解决没有 我现在在做PWM发送亚音 我的邮件是296073773@qq.com 您可否告知一下 随着频率变低 幅值不会跟着变低的解决方案 非常感谢 我是一个新人 目前项目优点紧急 只要你稍微点拨一下 对我的帮助都很大 谢谢师哥 我等您的消息    
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-7-23 17:21

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表