找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 968|回复: 1
打印 上一主题 下一主题
收起左侧

STC8A8K64S4A12单片机编写的SPWM,带软启动. 没测试

[复制链接]
跳转到指定楼层
楼主
ID:675799 发表于 2023-9-5 17:30 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
//一个SPWM带有死区的程序 用STC8A8K64S4A12单片机编写的SPWM
//介绍了一种高性能微机控制的单相 SPWM 变频调速系统  24000000L 增强型PWM
// SPWM信号经低通滤波后可变换为正弦波,窄带范围内的方波经低通滤波后可变换为相应频率的正弦波
//主时钟选择24MHZ, PWM时钟选择1T, PWM周期2400, 死区24个时钟(1us).正弦波表用200点.
//输出正弦波频率 = 24000000/ 2400 / 200 = 50 HZ.                   PWMC = 2400;
//PWM4输出选择P2.2          // PWM3输出选择P2.3, 无中断
//程序能用,如果不是你想要的频率,那就 自己改一下数据 记得同时要替换数组里面的值
#define         MAIN_Fosc                24000000L        //定义主时钟
#include        "STC8.H"
#include "intrins.h"           // _nop这个操作数用,ADC的。
unsigned int code T_SinTable[]={                                                   //50HZ         115幅值, 调制度10
1220, 1256, 1292, 1328, 1364, 1400, 1435, 1471, 1506, 1541,
1575, 1610, 1643, 1677, 1710, 1742, 1774, 1805, 1836, 1866,
1896, 1925, 1953, 1981, 2007, 2033, 2058, 2083, 2106, 2129,
2150, 2171, 2191, 2210, 2228, 2245, 2261, 2275, 2289, 2302,
2314, 2324, 2334, 2342, 2350, 2356, 2361, 2365, 2368, 2369,
2370, 2369, 2368, 2365, 2361, 2356, 2350, 2342, 2334, 2324,
2314, 2302, 2289, 2275, 2261, 2245, 2228, 2210, 2191, 2171,
2150, 2129, 2106, 2083, 2058, 2033, 2007, 1981, 1953, 1925,
1896, 1866, 1836, 1805, 1774, 1742, 1710, 1677, 1643, 1610,
1575, 1541, 1506, 1471, 1435, 1400, 1364, 1328, 1292, 1256,
1220, 1184, 1148, 1112, 1076, 1040, 1005, 969, 934, 899,
865, 830, 797, 763, 730, 698, 666, 635, 604, 574,
544, 515, 487, 459, 433, 407, 382, 357, 334, 311,
290, 269, 249, 230, 212, 195, 179, 165, 151, 138,
126, 116, 106, 98, 90, 84, 79, 75, 72, 71,
70, 71, 72, 75, 79, 84, 90, 98, 106, 116,
126, 138, 151, 165, 179, 195, 212, 230, 249, 269,
290, 311, 334, 357, 382, 407, 433, 459, 487, 515,
544, 574, 604, 635, 666, 698, 730, 763, 797, 830,
865, 899, 934, 969, 1005, 1040, 1076, 1112, 1148, 1184,
};
unsigned int code T_SinTable2[]={                                                   //50HZ         105幅值, 调制度10
1220,1252,1285,1318,1351,1384,1416,1449,1481,1512,
1544,1575,1606,1637,1667,1696,1725,1754,1782,1810,
1837,1863,1889,1914,1938,1962,1985,2007,2029,2049,
2069,2088,2106,2123,2140,2155,2170,2183,2196,2207,
2218,2228,2237,2244,2251,2257,2261,2265,2267,2269,
2270,2269,2267,2265,2261,2257,2251,2244,2237,2228,
2218,2207,2196,2183,2170,2155,2140,2123,2106,2088,
2069,2049,2029,2007,1985,1962,1938,1914,1889,1863,
1837,1810,1782,1754,1725,1696,1667,1637,1606,1575,
1544,1512,1481,1449,1416,1384,1351,1318,1285,1252,
1220,1187,1154,1121,1088,1055,1023,990,958,927,
895,864,833,802,772,743,714,685,657,629,
602,576,550,525,501,477,454,432,410,390,
370,351,333,316,299,284,269,256,243,232,
221,211,202,195,188,182,178,174,172,170,
170,170,172,174,178,182,188,195,202,211,
221,232,243,256,269,284,299,316,333,351,
370,390,410,432,454,477,501,525,550,576,
602,629,657,685,714,743,772,802,833,864,
895,927,958,990,1023,1055,1088,1121,1154,1187
};
unsigned int code T_SinTable3[]={                                                   //50HZ         95幅值, 调制度10
1220,1249,1279,1309,1339,1368,1398,1427,1456,1485,
1513,1541,1569,1597,1624,1651,1677,1703,1729,1753,
1778,1802,1825,1848,1870,1891,1912,1932,1951,1970,
1988,2005,2022,2037,2052,2066,2079,2091,2103,2113,
2123,2132,2140,2147,2153,2158,2162,2165,2168,2169,
2170,2169,2168,2165,2162,2158,2153,2147,2140,2132,
2123,2113,2103,2091,2079,2066,2052,2037,2022,2005,
1988,1970,1951,1932,1912,1891,1870,1848,1825,1802,
1778,1753,1729,1703,1677,1651,1624,1597,1569,1541,
1513,1485,1456,1427,1398,1368,1339,1309,1279,1249,
1220,1190,1160,1130,1100,1071,1041,1012,983,954,
926,898,870,842,815,788,762,736,710,686,
661,637,614,591,569,548,527,507,488,469,
451,434,417,402,387,373,360,348,336,326,
316,307,299,292,286,281,277,274,271,270,
270,270,271,274,277,281,286,292,299,307,
316,326,336,348,360,373,387,402,417,434,
451,469,488,507,527,548,569,591,614,637,
661,686,710,736,762,788,815,842,870,898,
926,954,983,1012,1041,1071,1100,1130,1160,1190 };

unsigned int code T_SinTable4[]={                                                   //50HZ         85幅值, 调制度10
1220,1246,1273,1299,1326,1352,1379,1405,1431,1457,
1482,1507,1532,1557,1581,1605,1629,1652,1675,1697,
1719,1740,1761,1782,1801,1821,1839,1857,1874,1891,
1907,1923,1937,1951,1964,1977,1989,2000,2010,2019,
2028,2036,2043,2049,2054,2059,2063,2066,2068,2069,
2070,2069,2068,2066,2063,2059,2054,2049,2043,2036,
2028,2019,2010,2000,1989,1977,1964,1951,1937,1923,
1907,1891,1874,1857,1839,1821,1801,1782,1761,1740,
1719,1697,1675,1652,1629,1605,1581,1557,1532,1507,
1482,1457,1431,1405,1379,1352,1326,1299,1273,1246,
1220,1193,1166,1140,1113,1087,1060,1034,1008,982,
957,932,907,882,858,834,810,787,764,742,
720,699,678,657,638,618,600,582,565,548,
532,516,502,488,475,462,450,439,429,420,
411,403,396,390,385,380,376,373,371,370,
370,370,371,373,376,380,385,390,396,403,
411,420,429,439,450,462,475,488,502,516,
532,548,565,582,600,618,638,657,678,699,
720,742,764,787,810,834,858,882,907,932,
957,982,1008,1034,1060,1087,1113,1140,1166,1193
  };
unsigned int code T_SinTable5[]={                                                   //50HZ         75幅值, 调制度10
1220,1243,1267,1290,1313,1337,1360,1383,1406,1429,
1451,1474,1496,1517,1539,1560,1581,1601,1621,1641,
1660,1679,1698,1715,1733,1750,1766,1782,1797,1812,
1826,1840,1853,1865,1877,1888,1898,1908,1917,1925,
1933,1940,1946,1951,1956,1960,1964,1966,1968,1969,
1970,1969,1968,1966,1964,1960,1956,1951,1946,1940,
1933,1925,1917,1908,1898,1888,1877,1865,1853,1840,
1826,1812,1797,1782,1766,1750,1733,1715,1698,1679,
1660,1641,1621,1601,1581,1560,1539,1517,1496,1474,
1451,1429,1406,1383,1360,1337,1313,1290,1267,1243,
1220,1196,1172,1149,1126,1102,1079,1056,1033,1010,
988,965,943,922,900,879,858,838,818,798,
779,760,741,724,706,689,673,657,642,627,
613,599,586,574,562,551,541,531,522,514,
506,499,493,488,483,479,475,473,471,470,
470,470,471,473,475,479,483,488,493,499,
506,514,522,531,541,551,562,574,586,599,
613,627,642,657,673,689,706,724,741,760,
779,798,818,838,858,879,900,922,943,965,
988,1010,1033,1056,1079,1102,1126,1149,1172,1196
};
unsigned int code T_SinTable6[]={                                                   //50HZ         65幅值, 调制度10
1220,1240,1260,1281,1301,1321,1341,1361,1381,1401,
1420,1440,1459,1478,1496,1515,1533,1550,1568,1585,
1602,1618,1634,1649,1664,1679,1693,1707,1720,1733,
1745,1757,1768,1779,1789,1799,1808,1816,1824,1831,
1838,1844,1849,1854,1858,1861,1864,1867,1868,1869,
1870,1869,1868,1867,1864,1861,1858,1854,1849,1844,
1838,1831,1824,1816,1808,1799,1789,1779,1768,1757,
1745,1733,1720,1707,1693,1679,1664,1649,1634,1618,
1602,1585,1568,1550,1533,1515,1496,1478,1459,1440,
1420,1401,1381,1361,1341,1321,1301,1281,1260,1240,
1220,1199,1179,1158,1138,1118,1098,1078,1058,1038,
1019,999,980,961,943,924,906,889,871,854,
837,821,805,790,775,760,746,732,719,706,
694,682,671,660,650,640,631,623,615,608,
601,595,590,585,581,578,575,572,571,570,
570,570,571,572,575,578,581,585,590,595,
601,608,615,623,631,640,650,660,671,682,
694,706,719,732,746,760,775,790,805,821,
837,854,871,889,906,924,943,961,980,999,
1019,1038,1058,1078,1098,1118,1138,1158,1179,1199
};
unsigned int code T_SinTable7[]={                                                   //50HZ         55幅值, 调制度10
1220,1237,1254,1271,1288,1306,1323,1339,1356,1373,
1389,1406,1422,1438,1454,1469,1484,1499,1514,1529,
1543,1557,1570,1583,1596,1608,1620,1632,1643,1654,
1664,1674,1684,1693,1701,1710,1717,1724,1731,1737,
1743,1748,1752,1756,1760,1763,1765,1767,1768,1769,
1770,1769,1768,1767,1765,1763,1760,1756,1752,1748,
1743,1737,1731,1724,1717,1710,1701,1693,1684,1674,
1664,1654,1643,1632,1620,1608,1596,1583,1570,1557,
1543,1529,1514,1499,1484,1469,1454,1438,1422,1406,
1389,1373,1356,1339,1323,1306,1288,1271,1254,1237,
1220,1202,1185,1168,1151,1133,1116,1100,1083,1066,
1050,1033,1017,1001,985,970,955,940,925,910,
896,882,869,856,843,831,819,807,796,785,
775,765,755,746,738,729,722,715,708,702,
696,691,687,683,679,676,674,672,671,670,
670,670,671,672,674,676,679,683,687,691,
696,702,708,715,722,729,738,746,755,765,
775,785,796,807,819,831,843,856,869,882,
896,910,925,940,955,970,985,1001,1017,1033,
1050,1066,1083,1100,1116,1133,1151,1168,1185,1202
};
unsigned int code T_SinTable8[]={                                                   //50HZ         45幅值, 调制度10
1220,1234,1248,1262,1276,1290,1304,1318,1331,1345,
1359,1372,1385,1398,1411,1424,1436,1449,1461,1472,
1484,1495,1506,1517,1528,1538,1548,1557,1566,1575,
1584,1592,1599,1607,1614,1620,1627,1632,1638,1643,
1647,1652,1655,1659,1662,1664,1666,1668,1669,1669,
1670,1669,1669,1668,1666,1664,1662,1659,1655,1652,
1647,1643,1638,1632,1627,1620,1614,1607,1599,1592,
1584,1575,1566,1557,1548,1538,1528,1517,1506,1495,
1484,1472,1461,1449,1436,1424,1411,1398,1385,1372,
1359,1345,1331,1318,1304,1290,1276,1262,1248,1234,
1220,1205,1191,1177,1163,1149,1135,1121,1108,1094,
1080,1067,1054,1041,1028,1015,1003,990,978,967,
955,944,933,922,911,901,891,882,873,864,
855,847,840,832,825,819,812,807,801,796,
792,787,784,780,777,775,773,771,770,770,
770,770,770,771,773,775,777,780,784,787,
792,796,801,807,812,819,825,832,840,847,
855,864,873,882,891,901,911,922,933,944,
955,967,978,990,1003,1015,1028,1041,1054,1067,
1080,1094,1108,1121,1135,1149,1163,1177,1191,1205
};               
         
unsigned int code T_SinT[]={          //50HZ         35幅值, 调制度10         //第一次启动用, 以后当临时数组。
1220,1230,1241,1252,1263,1274,1285,1296,1307,1317,
1328,1338,1348,1359,1369,1378,1388,1398,1407,1416,
1425,1434,1443,1451,1459,1467,1475,1482,1489,1496,
1503,1509,1515,1521,1526,1531,1536,1541,1545,1549,
1552,1556,1559,1561,1563,1565,1567,1568,1569,1569,
1570,1569,1569,1568,1567,1565,1563,1561,1559,1556,
1552,1549,1545,1541,1536,1531,1526,1521,1515,1509,
1503,1496,1489,1482,1475,1467,1459,1451,1443,1434,
1425,1416,1407,1398,1388,1378,1369,1359,1348,1338,
1328,1317,1307,1296,1285,1274,1263,1252,1241,1230,
1220,1209,1198,1187,1176,1165,1154,1143,1132,1122,
1111,1101,1091,1080,1070,1061,1051,1041,1032,1023,
1014,1005,996,988,980,972,964,957,950,943,
936,930,924,918,913,908,903,898,894,890,
887,883,880,878,876,874,873,872,871,871,
870,871,871,872,873,874,876,878,880,883,
887,890,894,898,903,908,913,918,924,930,
936,943,950,957,964,972,980,988,996,1005,
1014,1023,1032,1041,1051,1061,1070,1080,1091,1101,
1111,1122,1132,1143,1154,1165,1176,1187,1198,1209
          };        
#define        PwmClk_1T        0
#define        PwmClk_2T        1
#define        PwmClk_3T        2
#define        PwmClk_4T        3
#define        PwmClk_5T        4
#define        PwmClk_6T        5
#define        PwmClk_7T        6
#define        PwmClk_8T        7
#define        PwmClk_9T        8
#define        PwmClk_10T        9
#define        PwmClk_11T        10
#define        PwmClk_12T        11
#define        PwmClk_13T        12
#define        PwmClk_14T        13
#define        PwmClk_15T        14
#define        PwmClk_16T        15
#define        PwmClk_T2        16
#define        EAXSFR()                P_SW2 |=  0x80        /* MOVX A,@DPTR/MOVX @DPTR,A指令的操作对象为扩展SFR(XSFR) */
#define        EAXRAM()                P_SW2 &= ~0x80        /* MOVX A,@DPTR/MOVX @DPTR,A指令的操作对象为扩展RAM(XRAM) */
#define        PWM_Enable()        PWMCR |=  0x80        /* 使能PWM波形发生器,PWM计数器开始计数 */
#define        PWM_Disable()        PWMCR &= ~0x80        /* 关闭PWM波形发生器 */
#define P2n_standard(bitn)                        P2M1 &= ~(bitn),        P2M0 &= ~(bitn)
#define P2n_push_pull(bitn)                        P2M1 &= ~(bitn),        P2M0 |=  (bitn)
#define P2n_pure_input(bitn)                P2M1 |=  (bitn),        P2M0 &= ~(bitn)
#define P2n_open_drain(bitn)                P2M1 |=  (bitn),        P2M0 |=  (bitn)
#define                PWM_VECTOR                22
#define                PWM_DeadZone        24       /* 死区时钟数, 6 ~ 24之间 24个时钟是 1us */
typedef unsigned char         u8;
typedef unsigned int          u16;
typedef unsigned long         u32;

sbit LED_OUT =P3^3;
#define Port P1                         //设置CPU和模块的通讯接口
u8        PWM_Index;        //SPWM查表索引
u8   dt4 ; // 4秒内或 10次过流启动。
  u16 dtt;//开机标志



//sfr P2M0 = 0x96;         //P2口引脚模式寄存器
//sfr P1M0 = 0x92;         //P1口引脚模式寄存器
//sfr ADCCFG          = 0xDE;//   ADC 配置寄存器 DEH - - RESFMT - SPEED[3:0] xx0x,0000           RESFMT:ADC 转换结果格式控制位,默认左对齐。
//sfr ADC_CONTR = 0xBC;//A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]  ADC_POWER,SPEED1,SPEED0,ADC_FLAG,ADC_START,CHS2,CHS1,CHS0;0000,0000
//sfr ADC_RES   = 0xBD;//A/D 转换结果高8位  ADCV.9 ADCV.8 ADCV.7 ADCV.6 ADCV.5 ADCV.4 ADCV.3 ADCV.2;0000,0000
//sfr ADC_RESL  = 0xBE;//A/D 转换结果低2位                                            ADCV.1 ADCV.0;0000,0000



//sfr ADC_CHS[3:0] = 0x07        ;         //第 x.7通道
#define ADC_POWER        0x80        //ADC电源控制位
#define ADC_FLAG        0x20        //ADC完成标志位
#define ADC_START        0x40        //ADC启动控制位        #define ADC_START        0x08
#define ADC_SPEED0        0x02        //ADC转换速度,一次转换需要96个时钟
#define ADC_SPEED1        0x05        //ADC转换速度,一次转换需要192个时钟
#define ADC_SPEED2        0x0b        //ADC转换速度,一次转换需要364个时钟
#define ADC_SPEED3        0x0f        //ADC转换速度,一次转换需要512个时钟
#define N 8        //ADC采样使用递推平均滤波算法,采样次数
/******************************
函数说明:初始化ADC寄存器,设置P1.7为ADC输入功能
入口参数:无
出口参数:无
******************************/
void Init_ADC(void)
{   P1M0=0x00;
    P1M1=0x80;//  P1ASF = 0x80;                //打开P1.7口的ADC功能 (1000 0000 )
        ADC_RES = 0;        
        ADC_RESL= 0;                //清掉ADC转换结果寄存器
    ADC_CONTR = ADC_POWER ;        //使能A/D供电,

        ADCCFG=        ADC_SPEED3;        //设置转换速度90T  不设置速度, 采用PWM 计数器触发采样点。硬件自动触发 A/D 转换
   //sfr ADCCFG          = 0xDE;//   ADC 配置寄存器 DEH - - RESFMT - SPEED[3:0] xx0x,0000           RESFMT:ADC 转换结果格式控制位,默认左对齐。
//sfr ADC_CONTR = 0xBC;//A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]  ADC_POWER,SPEED1,SPEED0,ADC_FLAG,ADC_START,CHS2,CHS1,CHS0;0000,0000


}

/******************************
函数说明:查询方式读取ADC转换结果
入口参数:ch  ADC采样通道
出口参数:int ADC_RES ADC转换结果
******************************/
unsigned int Get_ADC_Result(unsigned char ch)
{
        unsigned int result;   //u16
        result =0 ;
        ADC_RES = 0;        
        ADC_RESL= 0;                                        //清掉ADC转换结果寄存器
        ADCCFG=        ADC_SPEED3;
        ADC_CONTR =ADC_POWER|ADC_START|ch;//配置ADC,设置转换通道,启动转换        /A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]
    _nop_();        _nop_();
    _nop_();        _nop_();                        //等待设置ADC_POWER完毕
    while (!(ADC_CONTR & ADC_FLAG));//读取转换完毕标志位ADC_FLAG
    ADC_CONTR &= ~ADC_FLAG;         //清除ADC_FLAG标志位
        result = ADC_RES<<4|ADC_RESL;        //读取12位转换结果保存到result
    return result;                  //返回ADC转换结果12位
}
/******************************/

/******************************/
void Delay1000ms()                //@24.000MHz
{
        unsigned char data i, j, k;

        _nop_();
        _nop_();
        i = 92;
        j = 50;
        k = 238;
        do
        {
                do
                {
                        while (--k);
                } while (--j);
        } while (--i);
}
//========================================================================
// 函数: void        PWM_config(void)
// 描述: PWM配置函数。
// 参数: none.
// 返回: none.
// 版本: VER1.0
// 日期:
// 备注:
//========================================================================
void        PWM_config(void)
{
  EAXSFR();                        // 访问XFR
  PWM3T1 = 65; // 第一个翻转计数
  PWM3T2=1220;         // 第二个翻转计数
  PWM3CR =0;         // PWM3输出选择P2.3, 无中断    pwm切换  有端口介绍(固定几个口)
  PWM3CR  |=  0x80;        // 相应PWM通道的端口为PWM输出口,受PWM波形发生器控制 ENC30
  PWM3CR &= ~0x40;        // 设置PWM输出端口的初始电平为0 C3INI
  P23 = 0;
  P2n_push_pull(1<<3);        //IO初始化, 上电时为高阻
  PWM4T1= 65-PWM_DeadZone;                        // 第一个翻转计数低字节
  PWM4T2 = (1220+PWM_DeadZone); // 第二个翻转计数高字节
  PWM4CR = 0;        // PWM4输出选择P2.2, 无中断
  PWM4CR  |=  0x80;        // 相应PWM通道的端口为PWM输出口,受PWM波形发生器控制 ENC40
  //        PWMCFG &= ~0x04;        // 设置PWM输出端口的初始电平为0  C4INI
  PWM4CR |=  0x40;        // 设置PWM输出端口的初始电平为1
  P24 = 1;
  P2n_push_pull(1<<4);        //IO初始化, 上电时为高阻
  PWMC = 2400;        // PWM计数器的高字节           2550 为47HZ  2666为45HZ,   2400为50HZ
     P26 = 0;                   //MOS管下臂
         P27 = 0;                   //MOS管下臂
  PWMCKS = PwmClk_1T;        // 时钟源: PwmClk_1T,PwmClk_2T, ... PwmClk_16T, PwmClk_Timer2
   IP2H=PPWMFDH; //pwm异常检测寄存器高位1, 为第3级。 ( 可以设置最高级4,加上 IP2=PPWMFD;) //设置PWM异常检测优先级3
  EAXRAM();                        // 恢复访问XRAM
////////////////////////////////
  PWMFDCR = ENFD  | FDIO; //PWM失效中断控制,  FLTFLIO=1发生 WM 外部异常时,PWM 的输出口立即被置为高阻模式??
            //FDIO==1 , 为P35,做为中断异常检测口;void PWMFD_Routine(void) interrupt 23;
  PWMCR |= ENPWM;                // 使能PWM波形发生器,PWM计数器开始计数
  //        PWMCR &= ~ECBI;                // 禁止PWM计数器归零中断
  PWMCR |=  ECBI;                // 允许PWM计数器归零中断


  PWMCFG=0x20 ; //ETADC  1:PWM 与 ADC 相关联。允许在 PWM 周期中某个时间点触发 A/D 转换。使用 TADCPH 和 TADCPL进行设置。
        //           在 ETADC=1 且 ADC_POWER=1 时,{TADCPH,TADCPL}组成一个 15 位的寄存器。在 PWM 的计数周
//期中,当 PWM 的内部计数值与{TADCPH,TADCPL}的值相等时,硬件自动触发 A/D 转换
   TADCPL=0x80;
   TADCPH =0x01;                                  //2400 pwm总计数2400 ;    600点 1800就是2个上下最大计数值。 取600。
}
//**********************************************/
                                                                                                           

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

void main(void)
{   u16 hvv,haa ;         //高压交流电压, 交流电流;
     u16 mvv; //直流320V 母线电压
         u8 g;
         dtt=0; //开机启动标志0

     PWM_Index = 0;                                                            

     LED_OUT =1;   //单片机开机指示
//         P35=0;         //MOS管 S过流电阻 , 过流==1   P35异常检测口
     P01=0;        //互感线圈过流         
     P02=0;           
     P03=0;          //不过流,温度高
         P04=0;   //温度高的,LED接口,指示用;
         P12=0;  //交流电压反馈           2.5V ==230v 输出有效值(最大值)ADC2 通道         ,这里用TL432的外部基准2.5v
         P17=0; //交流 电流反馈           2.5v ==8A  电流         (最大值)          adc7 通道
         P14=0; // 直流母线电压反馈 端口电阻分压到2.5V (最大值) =350V

             P1M0 &= ~0x94; P1M1 |= 0x94; //         //打开P17,P14 ,P12口的ADC功能(adc是高阻输入模式)
             Init_ADC();
                   PWM_config();        //初始化PWM    50hZ
         EA = 1;                //允许全局中断
                   PWM_Enable()   ;
            

  while (1)
  {                   hvv= Get_ADC_Result(2);        //将ADC P12电压调整,输出脉冲。让电流 在合理范围。
                haa= Get_ADC_Result(7);        //将ADC P17电压调整,输出脉冲。让电流 在合理范围。
            mvv= Get_ADC_Result(4);        //将ADC P14电压调整,输出脉冲。让电流 在合理范围。
                mvv=2.5*mvv/4069;  //外部基准为2.5v, 所以P14口,直流母线真是电压值 (母线电压有电阻分压到2.5V,经过LM358运放 给P14.)   
                //这个真实值 到底mvv单位是V??? 还是mv ??????????????          如果直流母线电压大于385V,也LED提示。
                if(mvv<2.25||mvv>2.75)          //2.4v还是2400mv实际测试决定一下。。。。。。
                { P02=1; } //P02接LED指示350v母线电压偏低,或者没有电压,或者电压大于385V
                 else { P02=0; } ;
               
               
                 if( P03==1) //温度高,停机或延时几十秒,启动。 由热敏电阻,检测后经LM358,送3v高电平到 p03口。
                   {     PWM_Disable() ; //关闭 PWM
                         PWM_Index=0;
                             P26=0;   P27=0;         //关闭2个 P26 P27方波口。
                                for(  g=1;g++;g<100)
                                {Delay1000ms();
                                P04= ~P04;    //LED指示闪,表示温度高; 冷却中;
                                
                                }  //冷却100秒再开机;
                                
                                 PWM_config();
                                 dtt=999;       //开机标志   
                                 PWM_Enable()   ;
                   }
                  
                  
                  
                   if(dt4==1)                                 //异常处理完后,再开机 主要是过流异常。
                        {
                               //其他需要处理异常的语句,在此加入。
                         dtt=0;         //二次降压开机模式 ,一样标志为999
                         PWM_config();        //初始化PWM    50hZ                     
                         PWM_Enable()   ;
                        
                         }
                  

  }
}
/********************* PWM中断函数************************/
void PWM_int (void) interrupt PWM_VECTOR
{        
  u16      j,  k;
  u8        SW2_tmp;
  if(PWMCFG & CBIF)        //PWM计数器归零中断标志 PWMCFG
  {
    PWMCFG &= ~CBIF;        //清除中断标志
    SW2_tmp = P_SW2;        //保存SW2设置
    EAXSFR();                //访问XFR
                                   ////////////////////////////////////////////////////////////////////////////////////////
                                if(dt4==1||dtt<=200)//PWM异常处理 过流,完成后 。尝试降压启动,数组用        ,开机启动999也是从此开
                                {            dtt++; //开机标志999, dt4==1是过流,
                                        j=T_SinTable8[PWM_Index];        // 第一次,最低电压启动        8级        或冲击电流大后,重新开机。
                                         dt4++;
                                }
                           if(dtt>200&&dtt<=400)                        //200点后,换波形                          // 第2个波形,低电压 7        级
                           { j=T_SinTable7[PWM_Index];
                                  dtt++;
                                }
                                   if(dtt>400&&dtt<=600)                                                          // 第3个波形,低电压启动6        级
                           { j=T_SinTable6[PWM_Index];
                                   dtt++;
                                }
                                  if(dtt>600&&dtt<=800)                                                          // 第4,低电压启动5        级
                           { j=T_SinTable5[PWM_Index];
                                  dtt++        ;
                                }
                             if(dtt>=800&&dtt<1000)                                                                             // 第5波,低电压启动4        级                           { j=T_SinTable4[PWM_Index];
                                  dtt++        ;
                                }
                                 if(dtt>=1000&&dtt<1200)                                                  // 第6波,低电压启动3        级
                           { j=T_SinTable3[PWM_Index];
                                  dtt++        ;
                                }
                                 if(dtt>=1200&&dtt<1400)                                                          // 第7波,低电压启动2        级
                           { j=T_SinTable2[PWM_Index];
                                  dtt++;
                                }
                                                   if(dtt>=1400)                                                  // 第8波,低电压启动1        级
                           { j=T_SinTable[PWM_Index];
                                                                                   
                                 
                                }
                          ///////////////////////////////////////////////////////////////////////////
                          

        k = j ;

    PWM3T2H = (u8)(j >> 8);        //第二个翻转计数高字节
    PWM3T2L  = (u8)j;              //第二个翻转计数低字节
        
               
    j += PWM_DeadZone;                //死区

    // 指向PWM4
    PWM4T2H = (u8)(j >> 8);        //第二个翻转计数高字节
    PWM4T2L = (u8)j;                        //第二个翻转计数低字节
    P_SW2 = SW2_tmp;        //恢复SW2设置
                             
    if(++PWM_Index <= 200)   
             PWM_Index = 0;
  }                 
  ///////////////////////////
          if(PWM_Index<=99 )                   ///////////  每100个点  2个下管 轮流对应 40或45或 50hz方波  p2.6 p.27初值,  要与 上管, 的初值 相反。
{  P26=0;
           _nop_();
        _nop_();
   P27=1;
}
          if(PWM_Index>99 )
{        P26=1;
    _nop_();
        _nop_();
        P27=0;                                 
                }
                                                      
         }         
                 /********************* PWM异常中断函数************************/
                 void PWMFD_Routine(void) interrupt 23
                {                if(         PWMFDCR  &=EFDI)
                         PWMFDCR  &=~EFDI  ;//清0 PWM异常检测寄存器的EFDI异常标志。                 
                            PWM_Disable() ; //关闭 PWM
                          P26=0;   P27=0;         //关闭2个 P26 P27方波口。

                              dtt=0;   //          再从0起。
                                PWM_Index=0;        // 正弦波表,再从0起。
                                dt4=1;        //异常计数 开始
                           
                            P41=1;
                                 Delay1000ms();        //异常后延时1秒。
                                 P41=0;                        //P41可以接LED灯。
                                                                                                     
                                }
分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏1 分享淘帖 顶 踩
回复

使用道具 举报

沙发
ID:675799 发表于 2023-9-7 14:36 | 只看该作者
//一个SPWM带有死区的程序 用STC8A8K64S4A12单片机编写的SPWM
//介绍了一种高性能微机控制的单相 SPWM 变频调速系统  24000000L 增强型PWM
// SPWM信号经低通滤波后可变换为正弦波,窄带范围内的方波经低通滤波后可变换为相应频率的正弦波
//主时钟选择24MHZ, PWM时钟选择1T, PWM周期2400, 死区24个时钟(1us).正弦波表用200点.
//输出正弦波频率 = 24000000/ 2400 / 200 = 50 HZ.                   PWMC = 2400;
//PWM4输出选择P2.4         // PWM3输出选择P2.3, 无中断
//程序能用,如果不是你想要的频率,那就 自己改一下数据 记得同时要替换数组里面的值
#define         MAIN_Fosc                24000000L        //定义主时钟
#include        "STC8.H"
#include "intrins.h"           // _nop这个操作数用,ADC的。
unsigned int code T_SinTable[]={                                                   //50HZ         115幅值, 调制度10
1220, 1256, 1292, 1328, 1364, 1400, 1435, 1471, 1506, 1541,
1575, 1610, 1643, 1677, 1710, 1742, 1774, 1805, 1836, 1866,
1896, 1925, 1953, 1981, 2007, 2033, 2058, 2083, 2106, 2129,
2150, 2171, 2191, 2210, 2228, 2245, 2261, 2275, 2289, 2302,
2314, 2324, 2334, 2342, 2350, 2356, 2361, 2365, 2368, 2369,
2370, 2369, 2368, 2365, 2361, 2356, 2350, 2342, 2334, 2324,
2314, 2302, 2289, 2275, 2261, 2245, 2228, 2210, 2191, 2171,
2150, 2129, 2106, 2083, 2058, 2033, 2007, 1981, 1953, 1925,
1896, 1866, 1836, 1805, 1774, 1742, 1710, 1677, 1643, 1610,
1575, 1541, 1506, 1471, 1435, 1400, 1364, 1328, 1292, 1256,
1220, 1184, 1148, 1112, 1076, 1040, 1005, 969, 934, 899,
865, 830, 797, 763, 730, 698, 666, 635, 604, 574,
544, 515, 487, 459, 433, 407, 382, 357, 334, 311,
290, 269, 249, 230, 212, 195, 179, 165, 151, 138,
126, 116, 106, 98, 90, 84, 79, 75, 72, 71,
70, 71, 72, 75, 79, 84, 90, 98, 106, 116,
126, 138, 151, 165, 179, 195, 212, 230, 249, 269,
290, 311, 334, 357, 382, 407, 433, 459, 487, 515,
544, 574, 604, 635, 666, 698, 730, 763, 797, 830,
865, 899, 934, 969, 1005, 1040, 1076, 1112, 1148, 1184,
};
unsigned int code T_SinTable2[]={                                                   //50HZ         105幅值, 调制度10
1220,1252,1285,1318,1351,1384,1416,1449,1481,1512,
1544,1575,1606,1637,1667,1696,1725,1754,1782,1810,
1837,1863,1889,1914,1938,1962,1985,2007,2029,2049,
2069,2088,2106,2123,2140,2155,2170,2183,2196,2207,
2218,2228,2237,2244,2251,2257,2261,2265,2267,2269,
2270,2269,2267,2265,2261,2257,2251,2244,2237,2228,
2218,2207,2196,2183,2170,2155,2140,2123,2106,2088,
2069,2049,2029,2007,1985,1962,1938,1914,1889,1863,
1837,1810,1782,1754,1725,1696,1667,1637,1606,1575,
1544,1512,1481,1449,1416,1384,1351,1318,1285,1252,
1220,1187,1154,1121,1088,1055,1023,990,958,927,
895,864,833,802,772,743,714,685,657,629,
602,576,550,525,501,477,454,432,410,390,
370,351,333,316,299,284,269,256,243,232,
221,211,202,195,188,182,178,174,172,170,
170,170,172,174,178,182,188,195,202,211,
221,232,243,256,269,284,299,316,333,351,
370,390,410,432,454,477,501,525,550,576,
602,629,657,685,714,743,772,802,833,864,
895,927,958,990,1023,1055,1088,1121,1154,1187
};
unsigned int code T_SinTable3[]={                                                   //50HZ         95幅值, 调制度10
1220,1249,1279,1309,1339,1368,1398,1427,1456,1485,
1513,1541,1569,1597,1624,1651,1677,1703,1729,1753,
1778,1802,1825,1848,1870,1891,1912,1932,1951,1970,
1988,2005,2022,2037,2052,2066,2079,2091,2103,2113,
2123,2132,2140,2147,2153,2158,2162,2165,2168,2169,
2170,2169,2168,2165,2162,2158,2153,2147,2140,2132,
2123,2113,2103,2091,2079,2066,2052,2037,2022,2005,
1988,1970,1951,1932,1912,1891,1870,1848,1825,1802,
1778,1753,1729,1703,1677,1651,1624,1597,1569,1541,
1513,1485,1456,1427,1398,1368,1339,1309,1279,1249,
1220,1190,1160,1130,1100,1071,1041,1012,983,954,
926,898,870,842,815,788,762,736,710,686,
661,637,614,591,569,548,527,507,488,469,
451,434,417,402,387,373,360,348,336,326,
316,307,299,292,286,281,277,274,271,270,
270,270,271,274,277,281,286,292,299,307,
316,326,336,348,360,373,387,402,417,434,
451,469,488,507,527,548,569,591,614,637,
661,686,710,736,762,788,815,842,870,898,
926,954,983,1012,1041,1071,1100,1130,1160,1190 };

unsigned int code T_SinTable4[]={                                                   //50HZ         85幅值, 调制度10
1220,1246,1273,1299,1326,1352,1379,1405,1431,1457,
1482,1507,1532,1557,1581,1605,1629,1652,1675,1697,
1719,1740,1761,1782,1801,1821,1839,1857,1874,1891,
1907,1923,1937,1951,1964,1977,1989,2000,2010,2019,
2028,2036,2043,2049,2054,2059,2063,2066,2068,2069,
2070,2069,2068,2066,2063,2059,2054,2049,2043,2036,
2028,2019,2010,2000,1989,1977,1964,1951,1937,1923,
1907,1891,1874,1857,1839,1821,1801,1782,1761,1740,
1719,1697,1675,1652,1629,1605,1581,1557,1532,1507,
1482,1457,1431,1405,1379,1352,1326,1299,1273,1246,
1220,1193,1166,1140,1113,1087,1060,1034,1008,982,
957,932,907,882,858,834,810,787,764,742,
720,699,678,657,638,618,600,582,565,548,
532,516,502,488,475,462,450,439,429,420,
411,403,396,390,385,380,376,373,371,370,
370,370,371,373,376,380,385,390,396,403,
411,420,429,439,450,462,475,488,502,516,
532,548,565,582,600,618,638,657,678,699,
720,742,764,787,810,834,858,882,907,932,
957,982,1008,1034,1060,1087,1113,1140,1166,1193
  };
unsigned int code T_SinTable5[]={                                                   //50HZ         75幅值, 调制度10
1220,1243,1267,1290,1313,1337,1360,1383,1406,1429,
1451,1474,1496,1517,1539,1560,1581,1601,1621,1641,
1660,1679,1698,1715,1733,1750,1766,1782,1797,1812,
1826,1840,1853,1865,1877,1888,1898,1908,1917,1925,
1933,1940,1946,1951,1956,1960,1964,1966,1968,1969,
1970,1969,1968,1966,1964,1960,1956,1951,1946,1940,
1933,1925,1917,1908,1898,1888,1877,1865,1853,1840,
1826,1812,1797,1782,1766,1750,1733,1715,1698,1679,
1660,1641,1621,1601,1581,1560,1539,1517,1496,1474,
1451,1429,1406,1383,1360,1337,1313,1290,1267,1243,
1220,1196,1172,1149,1126,1102,1079,1056,1033,1010,
988,965,943,922,900,879,858,838,818,798,
779,760,741,724,706,689,673,657,642,627,
613,599,586,574,562,551,541,531,522,514,
506,499,493,488,483,479,475,473,471,470,
470,470,471,473,475,479,483,488,493,499,
506,514,522,531,541,551,562,574,586,599,
613,627,642,657,673,689,706,724,741,760,
779,798,818,838,858,879,900,922,943,965,
988,1010,1033,1056,1079,1102,1126,1149,1172,1196
};
unsigned int code T_SinTable6[]={                                                   //50HZ         65幅值, 调制度10
1220,1240,1260,1281,1301,1321,1341,1361,1381,1401,
1420,1440,1459,1478,1496,1515,1533,1550,1568,1585,
1602,1618,1634,1649,1664,1679,1693,1707,1720,1733,
1745,1757,1768,1779,1789,1799,1808,1816,1824,1831,
1838,1844,1849,1854,1858,1861,1864,1867,1868,1869,
1870,1869,1868,1867,1864,1861,1858,1854,1849,1844,
1838,1831,1824,1816,1808,1799,1789,1779,1768,1757,
1745,1733,1720,1707,1693,1679,1664,1649,1634,1618,
1602,1585,1568,1550,1533,1515,1496,1478,1459,1440,
1420,1401,1381,1361,1341,1321,1301,1281,1260,1240,
1220,1199,1179,1158,1138,1118,1098,1078,1058,1038,
1019,999,980,961,943,924,906,889,871,854,
837,821,805,790,775,760,746,732,719,706,
694,682,671,660,650,640,631,623,615,608,
601,595,590,585,581,578,575,572,571,570,
570,570,571,572,575,578,581,585,590,595,
601,608,615,623,631,640,650,660,671,682,
694,706,719,732,746,760,775,790,805,821,
837,854,871,889,906,924,943,961,980,999,
1019,1038,1058,1078,1098,1118,1138,1158,1179,1199
};
unsigned int code T_SinTable7[]={                                                   //50HZ         55幅值, 调制度10
1220,1237,1254,1271,1288,1306,1323,1339,1356,1373,
1389,1406,1422,1438,1454,1469,1484,1499,1514,1529,
1543,1557,1570,1583,1596,1608,1620,1632,1643,1654,
1664,1674,1684,1693,1701,1710,1717,1724,1731,1737,
1743,1748,1752,1756,1760,1763,1765,1767,1768,1769,
1770,1769,1768,1767,1765,1763,1760,1756,1752,1748,
1743,1737,1731,1724,1717,1710,1701,1693,1684,1674,
1664,1654,1643,1632,1620,1608,1596,1583,1570,1557,
1543,1529,1514,1499,1484,1469,1454,1438,1422,1406,
1389,1373,1356,1339,1323,1306,1288,1271,1254,1237,
1220,1202,1185,1168,1151,1133,1116,1100,1083,1066,
1050,1033,1017,1001,985,970,955,940,925,910,
896,882,869,856,843,831,819,807,796,785,
775,765,755,746,738,729,722,715,708,702,
696,691,687,683,679,676,674,672,671,670,
670,670,671,672,674,676,679,683,687,691,
696,702,708,715,722,729,738,746,755,765,
775,785,796,807,819,831,843,856,869,882,
896,910,925,940,955,970,985,1001,1017,1033,
1050,1066,1083,1100,1116,1133,1151,1168,1185,1202
};
unsigned int code T_SinTable8[]={                                                   //50HZ         45幅值, 调制度10
1220,1234,1248,1262,1276,1290,1304,1318,1331,1345,
1359,1372,1385,1398,1411,1424,1436,1449,1461,1472,
1484,1495,1506,1517,1528,1538,1548,1557,1566,1575,
1584,1592,1599,1607,1614,1620,1627,1632,1638,1643,
1647,1652,1655,1659,1662,1664,1666,1668,1669,1669,
1670,1669,1669,1668,1666,1664,1662,1659,1655,1652,
1647,1643,1638,1632,1627,1620,1614,1607,1599,1592,
1584,1575,1566,1557,1548,1538,1528,1517,1506,1495,
1484,1472,1461,1449,1436,1424,1411,1398,1385,1372,
1359,1345,1331,1318,1304,1290,1276,1262,1248,1234,
1220,1205,1191,1177,1163,1149,1135,1121,1108,1094,
1080,1067,1054,1041,1028,1015,1003,990,978,967,
955,944,933,922,911,901,891,882,873,864,
855,847,840,832,825,819,812,807,801,796,
792,787,784,780,777,775,773,771,770,770,
770,770,770,771,773,775,777,780,784,787,
792,796,801,807,812,819,825,832,840,847,
855,864,873,882,891,901,911,922,933,944,
955,967,978,990,1003,1015,1028,1041,1054,1067,
1080,1094,1108,1121,1135,1149,1163,1177,1191,1205
};               
         
unsigned int code T_SinT[]={          //50HZ         35幅值, 调制度10         //第一次启动用, 以后当临时数组。
1220,1230,1241,1252,1263,1274,1285,1296,1307,1317,
1328,1338,1348,1359,1369,1378,1388,1398,1407,1416,
1425,1434,1443,1451,1459,1467,1475,1482,1489,1496,
1503,1509,1515,1521,1526,1531,1536,1541,1545,1549,
1552,1556,1559,1561,1563,1565,1567,1568,1569,1569,
1570,1569,1569,1568,1567,1565,1563,1561,1559,1556,
1552,1549,1545,1541,1536,1531,1526,1521,1515,1509,
1503,1496,1489,1482,1475,1467,1459,1451,1443,1434,
1425,1416,1407,1398,1388,1378,1369,1359,1348,1338,
1328,1317,1307,1296,1285,1274,1263,1252,1241,1230,
1220,1209,1198,1187,1176,1165,1154,1143,1132,1122,
1111,1101,1091,1080,1070,1061,1051,1041,1032,1023,
1014,1005,996,988,980,972,964,957,950,943,
936,930,924,918,913,908,903,898,894,890,
887,883,880,878,876,874,873,872,871,871,
870,871,871,872,873,874,876,878,880,883,
887,890,894,898,903,908,913,918,924,930,
936,943,950,957,964,972,980,988,996,1005,
1014,1023,1032,1041,1051,1061,1070,1080,1091,1101,
1111,1122,1132,1143,1154,1165,1176,1187,1198,1209
          };        
#define        PwmClk_1T        0
#define        PwmClk_2T        1
#define        PwmClk_3T        2
#define        PwmClk_4T        3
#define        PwmClk_5T        4
#define        PwmClk_6T        5
#define        PwmClk_7T        6
#define        PwmClk_8T        7
#define        PwmClk_9T        8
#define        PwmClk_10T        9
#define        PwmClk_11T        10
#define        PwmClk_12T        11
#define        PwmClk_13T        12
#define        PwmClk_14T        13
#define        PwmClk_15T        14
#define        PwmClk_16T        15
#define        PwmClk_T2        16
#define        EAXSFR()                P_SW2 |=  0x80        /* MOVX A,@DPTR/MOVX @DPTR,A指令的操作对象为扩展SFR(XSFR) */
#define        EAXRAM()                P_SW2 &= ~0x80        /* MOVX A,@DPTR/MOVX @DPTR,A指令的操作对象为扩展RAM(XRAM) */
#define        PWM_Enable()        PWMCR |=  0x80        /* 使能PWM波形发生器,PWM计数器开始计数 */
#define        PWM_Disable()        PWMCR &= ~0x80        /* 关闭PWM波形发生器 */
#define P2n_standard(bitn)                        P2M1 &= ~(bitn),        P2M0 &= ~(bitn)
#define P2n_push_pull(bitn)                        P2M1 &= ~(bitn),        P2M0 |=  (bitn)
#define P2n_pure_input(bitn)                P2M1 |=  (bitn),        P2M0 &= ~(bitn)
#define P2n_open_drain(bitn)                P2M1 |=  (bitn),        P2M0 |=  (bitn)
#define                PWM_VECTOR                22
#define                PWM_DeadZone        24       /* 死区时钟数, 6 ~ 24之间 24个时钟是 1us */
typedef unsigned char         u8;
typedef unsigned int          u16;
typedef unsigned long         u32;

sbit LED_OUT =P3^3;
#define Port P1                         //设置CPU和模块的通讯接口
u8        PWM_Index;        //SPWM查表索引
u8   dt4 ; // 4秒内或 10次过流启动。
  u16 dtt;//开机标志



//sfr P2M0 = 0x96;         //P2口引脚模式寄存器
//sfr P1M0 = 0x92;         //P1口引脚模式寄存器
//sfr ADCCFG          = 0xDE;//   ADC 配置寄存器 DEH - - RESFMT - SPEED[3:0] xx0x,0000           RESFMT:ADC 转换结果格式控制位,默认左对齐。
//sfr ADC_CONTR = 0xBC;//A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]  ADC_POWER,SPEED1,SPEED0,ADC_FLAG,ADC_START,CHS2,CHS1,CHS0;0000,0000
//sfr ADC_RES   = 0xBD;//A/D 转换结果高8位  ADCV.9 ADCV.8 ADCV.7 ADCV.6 ADCV.5 ADCV.4 ADCV.3 ADCV.2;0000,0000
//sfr ADC_RESL  = 0xBE;//A/D 转换结果低2位                                            ADCV.1 ADCV.0;0000,0000



//sfr ADC_CHS[3:0] = 0x07        ;         //第 x.7通道
#define ADC_POWER        0x80        //ADC电源控制位
#define ADC_FLAG        0x20        //ADC完成标志位
#define ADC_START        0x40        //ADC启动控制位        #define ADC_START        0x08
#define ADC_SPEED0        0x02        //ADC转换速度,一次转换需要96个时钟
#define ADC_SPEED1        0x05        //ADC转换速度,一次转换需要192个时钟
#define ADC_SPEED2        0x0b        //ADC转换速度,一次转换需要364个时钟
#define ADC_SPEED3        0x0f        //ADC转换速度,一次转换需要512个时钟
#define N 8        //ADC采样使用递推平均滤波算法,采样次数
/******************************
函数说明:初始化ADC寄存器,设置P1.7为ADC输入功能
入口参数:无
出口参数:无
******************************/
void Init_ADC(void)
{   P1M0=0x00;
    P1M1=0x80;//  P1ASF = 0x80;                //打开P1.7口的ADC功能 (1000 0000 )
        ADC_RES = 0;        
        ADC_RESL= 0;                //清掉ADC转换结果寄存器
    ADC_CONTR = ADC_POWER ;        //使能A/D供电,

        ADCCFG=        ADC_SPEED3;        //设置转换速度90T  不设置速度, 采用PWM 计数器触发采样点。硬件自动触发 A/D 转换
   //sfr ADCCFG          = 0xDE;//   ADC 配置寄存器 DEH - - RESFMT - SPEED[3:0] xx0x,0000           RESFMT:ADC 转换结果格式控制位,默认左对齐。
//sfr ADC_CONTR = 0xBC;//A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]  ADC_POWER,SPEED1,SPEED0,ADC_FLAG,ADC_START,CHS2,CHS1,CHS0;0000,0000


}

/******************************
函数说明:查询方式读取ADC转换结果
入口参数:ch  ADC采样通道
出口参数:int ADC_RES ADC转换结果
******************************/
unsigned int Get_ADC_Result(unsigned char ch)
{
        unsigned int result;   //u16
        result =0 ;
        ADC_RES = 0;        
        ADC_RESL= 0;                                        //清掉ADC转换结果寄存器
        ADCCFG=        ADC_SPEED3;
        ADC_CONTR =ADC_POWER|ADC_START|ch;//配置ADC,设置转换通道,启动转换        /A/D 转换控制寄存器 ADC_POWER ADC_START ADC_FLAG - ADC_CHS[3:0]
    _nop_();        _nop_();
    _nop_();        _nop_();                        //等待设置ADC_POWER完毕
    while (!(ADC_CONTR & ADC_FLAG));//读取转换完毕标志位ADC_FLAG
    ADC_CONTR &= ~ADC_FLAG;         //清除ADC_FLAG标志位
        result = ADC_RES<<4|ADC_RESL;        //读取12位转换结果保存到result
    return result;                  //返回ADC转换结果12位
}
/******************************/

/******************************/
void Delay1000ms()                //@24.000MHz
{
        unsigned char data i, j, k;

        _nop_();
        _nop_();
        i = 92;
        j = 50;
        k = 238;
        do
        {
                do
                {
                        while (--k);
                } while (--j);
        } while (--i);
}
//========================================================================
// 函数: void        PWM_config(void)
// 描述: PWM配置函数。
// 参数: none.
// 返回: none.
// 版本: VER1.0
// 日期:
// 备注:
//========================================================================
void        PWM_config(void)
{
  EAXSFR();                        // 访问XFR
  PWM3T1 = 65; // 第一个翻转计数
  PWM3T2=1220;         // 第二个翻转计数
  PWM3CR =0;         // PWM3输出选择P2.3, 无中断    pwm切换  有端口介绍(固定几个口)
  PWM3CR  |=  0x80;        // 相应PWM通道的端口为PWM输出口,受PWM波形发生器控制 ENC30
  PWM3CR &= ~0x40;        // 设置PWM输出端口的初始电平为0 C3INI
  P23 = 0;
  P2n_push_pull(1<<3);        //IO初始化, 上电时为高阻
  PWM4T1= 65-PWM_DeadZone;                        // 第一个翻转计数低字节
  PWM4T2 = (1220+PWM_DeadZone); // 第二个翻转计数高字节
  PWM4CR = 0;        // PWM4输出选择P2.4, 无中断
  PWM4CR  |=  0x80;        // 相应PWM通道的端口为PWM输出口,受PWM波形发生器控制 ENC40
  //        PWMCFG &= ~0x04;        // 设置PWM输出端口的初始电平为0  C4INI
  PWM4CR |=  0x40;        // 设置PWM输出端口的初始电平为1
  P24 = 1;
  P2n_push_pull(1<<4);        //IO初始化, 上电时为高阻
  PWMC = 2400;        // PWM计数器的高字节           
     P26 = 0;                   //MOS管下臂
         P27 = 0;                   //MOS管下臂
  PWMCKS = PwmClk_1T;        // 时钟源: PwmClk_1T,PwmClk_2T, ... PwmClk_16T, PwmClk_Timer2
   IP2H=PPWMFDH; //pwm异常检测寄存器高位1, 为第3级。 ( 可以设置最高级4,加上 IP2=PPWMFD;) //设置PWM异常检测优先级3
  EAXRAM();                        // 恢复访问XRAM
////////////////////////////////
  PWMFDCR = ENFD  | FDIO; //PWM失效中断控制,  FLTFLIO=1发生 WM 外部异常时,PWM 的输出口立即被置为高阻模式??
            //FDIO==1 , 为P35,做为中断异常检测口;void PWMFD_Routine(void) interrupt 23;
  PWMCR |= ENPWM;                // 使能PWM波形发生器,PWM计数器开始计数
  //        PWMCR &= ~ECBI;                // 禁止PWM计数器归零中断
  PWMCR |=  ECBI;                // 允许PWM计数器归零中断


  PWMCFG=0x20 ; //ETADC  1:PWM 与 ADC 相关联。允许在 PWM 周期中某个时间点触发 A/D 转换。使用 TADCPH 和 TADCPL进行设置。
        //           在 ETADC=1 且 ADC_POWER=1 时,{TADCPH,TADCPL}组成一个 15 位的寄存器。在 PWM 的计数周
//期中,当 PWM 的内部计数值与{TADCPH,TADCPL}的值相等时,硬件自动触发 A/D 转换
   TADCPL=0x80;
   TADCPH =0x01;                                  //2400 pwm总计数2400 ;    600点 1800就是2个上下最大计数值。 取600。
}
//**********************************************/
                                                                                                           

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

void main(void)
{   u16 hvv,haa ,j;         //高压交流电压, 交流电流;
     u16 mvv; //直流320V 母线电压
         u8 g;
         dtt=0; //开机启动标志0
       PWM_Index = 0;        
          ////////////////////////////////////////////////////////////////////////////////////////
                                
                                                        

     LED_OUT =1;   //单片机开机指示
//         P35=0;         //MOS管 S过流电阻 , 过流==1   P35异常检测口
     P01=0;        //互感线圈过流         
     P02=0;           
     P03=0;          //不过流,温度高
         P04=0;   //温度高的,LED接口,指示用;
         P12=0;  //交流电压反馈           2.5V ==230v 输出有效值(最大值)ADC2 通道         ,这里用TL432的外部基准2.5v
         P17=0; //交流 电流反馈           2.5v ==8A  电流         (最大值)          adc7 通道
         P14=0; // 直流母线电压反馈 端口电阻分压到2.5V (最大值) =350V

             P1M0 &= ~0x94; P1M1 |= 0x94; //         //打开P17,P14 ,P12口的ADC功能(adc是高阻输入模式)
             Init_ADC();
                   PWM_config();        //初始化PWM    50hZ
         EA = 1;                //允许全局中断
                   PWM_Enable()   ;
            

  while (1)
  {                   hvv= Get_ADC_Result(2);        //将ADC P12电压调整,输出脉冲。让电流 在合理范围。
                haa= Get_ADC_Result(7);        //将ADC P17电压调整,输出脉冲。让电流 在合理范围。
            mvv= Get_ADC_Result(4);        //将ADC P14电压调整,输出脉冲。让电流 在合理范围。
                mvv=2.5*mvv/4069;  //外部基准为2.5v, 所以P14口,直流母线真是电压值 (母线电压有电阻分压到2.5V,经过LM358运放 给P14.)   
                //这个真实值 到底mvv单位是V??? 还是mv ??????????????          如果直流母线电压大于385V,也LED提示。
                if(mvv<2.25||mvv>2.75)          //2.4v还是2400mv实际测试决定一下。。。。。。
                { P02=1; } //P02接LED指示350v母线电压偏低,或者没有电压,或者电压大于385V 可以加入关闭PWM代码。
                 else { P02=0; } ;
               
                      P0M0 &= ~0x08; P0M1 |= 0x08;          //        P03设置为 高阻输入模式。开机记得接下拉电阻。

                 if( P03==1) //温度高,停机或延时几十秒,启动。 由热敏电阻,检测后经LM358,送3v高电平到 p03口。
                   {     PWM_Disable() ; //关闭 PWM
                         PWM_Index=0;
                             P26=0;   P27=0;         //关闭2个 P26 P27方波口。
                                for(  g=1;g++;g<100)
                                {Delay1000ms();
                                P04= ~P04;    //LED指示闪,表示温度高; 冷却中;
                                
                                }  //冷却100秒再开机;
                                
                                 PWM_config();
                                 dtt=0;       //开机标志   
                                 PWM_Enable()   ;
                   }
                  
                  
                  
                   if(dt4==1)                                 //异常处理完后,再开机 主要是过流异常。
                        {
                               //其他需要处理异常的语句,在此加入。
                         dtt=0;         //二次降压开机模式 ,一样标志为0
                         PWM_config();        //初始化PWM    50hZ                     
                         PWM_Enable()   ;
                        
                         }
                  

  }
}
/********************* PWM中断函数************************/
void PWM_int (void) interrupt PWM_VECTOR
{        
  u16      j,  k;
  u8        SW2_tmp;
  if(PWMCFG & CBIF)        //PWM计数器归零中断标志 PWMCFG
  {
    PWMCFG &= ~CBIF;        //清除中断标志
    SW2_tmp = P_SW2;        //保存SW2设置
    EAXSFR();                //访问XFR
                                   ////////////////////////////////////////////////////////////////////////////////////////
                                if(dt4==1||dtt<200)//PWM异常处理 过流,完成后 。尝试降压启动,数组用        ,开机启动999也是从此开
                                {            dtt++; //开机标志999, dt4==1是过流,
                                        j=T_SinTable8[PWM_Index];        // 第一次,最低电压启动        8级        或冲击电流大后,重新开机。
                                         dt4++;
                                }
                           if(dtt>=200&&dtt<400)                        //200点后,换波形                          // 第2个波形,低电压 7        级
                           { j=T_SinTable7[PWM_Index];
                                  dtt++;
                                }
                                   if(dtt>=400&&dtt<600)                                                          // 第3个波形,低电压启动6        级
                           { j=T_SinTable6[PWM_Index];
                                   dtt++;
                                }
                                  if(dtt>=600&&dtt<800)                                                          // 第4,低电压启动5        级
                           { j=T_SinTable5[PWM_Index];
                                  dtt++        ;
                                }
                                   if(dtt>=800&&dtt<1000)                                                                             // 第5波,低电压启动4        级
                           { j=T_SinTable4[PWM_Index];
                                  dtt++        ;
                                }
                                 if(dtt>=1200&&dtt<1400)                                                  // 第6波,低电压启动3        级
                           { j=T_SinTable3[PWM_Index];
                                  dtt++        ;
                                }
                                 if(dtt>=1400&&dtt<1600)                                                          // 第7波,低电压启动2        级
                           { j=T_SinTable2[PWM_Index];
                                  dtt++;
                                }
                                                   if(dtt>=1800)                                                  // 第8波,低电压启动1        级
                           { j=T_SinTable[PWM_Index];
                                                                                   
                                 
                                }
                          ///////////////////////////////////////////////////////////////////////////
                          

        k = j ;

    PWM3T2H = (u8)(j >> 8);        //第二个翻转计数高字节
    PWM3T2L  = (u8)j;              //第二个翻转计数低字节
        
               
    j += PWM_DeadZone;                //死区

    // 指向PWM4
    PWM4T2H = (u8)(j >> 8);        //第二个翻转计数高字节
    PWM4T2L = (u8)j;                        //第二个翻转计数低字节
    P_SW2 = SW2_tmp;        //恢复SW2设置
                             
    if(++PWM_Index >= 200)   
             PWM_Index = 0;
  }                 
  ///////////////////////////
          if(PWM_Index<=99 )                   ///////////  每100个点  2个下管 轮流对应 40或45或 50hz方波  p2.6 p.27初值,  要与 上管, 的初值 相反。
{  P26=0;
           _nop_();
        _nop_();
   P27=1;
}
          if(PWM_Index>99 )
{        P26=1;
    _nop_();
        _nop_();
        P27=0;                                 
                }
                                                      
         }         
                 /********************* PWM异常中断函数************************/
                 void PWMFD_Routine(void) interrupt 23
                {                     if(         PWMFDCR  &=FDIF)           //FDIF 中断请求位
                         PWMFDCR  &=~FDIF  ;//清0 PWM异常检测寄存器的  。                 
                            PWM_Disable() ; //关闭 PWM
                          P26=0;   P27=0;         //关闭2个 P26 P27方波口。

                              dtt=0;   //          再从0起。
                                PWM_Index=0;        // 正弦波表,再从0起。
                                dt4=1;        //异常计数 开始
                           
                            P41=1;
                                 Delay1000ms();        //异常后延时1秒。
                                 P41=0;                        //P41可以接LED灯。
                                                                                                     
                                }
        
                                    
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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