📄 lcdc_040.lst
字号:
220 1 SFRPAGE = CONFIG_PAGE; // switch to config page to config oscillator
221 1 OSCXCN = 0x77; // start external oscillator; 22.1 MHz Crystal
222 1 // system clock is 22.1 MHz / 2 = 11.05 MHz
223 1 for (n=0;n<255;n++); // delay about 1ms
224 1 while ((OSCXCN & 0x80) == 0); // wait for oscillator to stabilize
225 1 CLKSEL |= 0x01; // switch to external oscillator
226 1 }
227
228 void config_IO (void)//I/O端口初始化
229 {
230 1 SFRPAGE = CONFIG_PAGE; //Port SFR's on Configuration page
231 1 P0MDOUT=0xff;
232 1 XBR0 = 0x06;
233 1 XBR3 = 0x80; // Configure CAN TX pin (CTX) as push-pull digital output
234 1 // P1MDOUT |= 0x40; // Configure P1.6 as push-pull to drive LED
235 1 XBR2 = 0x40; // Enable Crossbar/low ports
236 1 }
237 ////////////////////////////////////////////////////////////////////////////////
238 //CAN Functions
239 ////////////////////////////////////////////////////////////////////////////////
240
241
C51 COMPILER V7.08 LCDC_040 04/24/2008 15:54:41 PAGE 5
242 //Clear Message Objects
243 void clear_msg_objects (void)//将所有消息清0
244 {
245 1 SFRPAGE = CAN0_PAGE;
246 1 //向CAN 相关寄存器写入数据的方法
247 1 //间接访问方式 地址索引寄存器指向索引号,相应数据写入数据寄存器
248 1 CAN0ADR = IF1CMDMSK; // Point to Command Mask Register 1
249 1 CAN0DATL = 0xFF; // Set direction to WRITE all IF registers to Msg Obj
250 1 for (i=1;i<33;i++)//32个消息对象
251 1 {
252 2 CAN0ADR = IF1CMDRQST; // Write blank (reset) IF registers to each msg obj
253 2 CAN0DATL = i;//Message Number 写入
254 2 }
255 1 }
256
257 //Initialize Message Object for RX
258 void init_msg_object_RX (char MsgNum,uint id)
259 { uint temp;
260 1 SFRPAGE = CAN0_PAGE;
261 1 CAN0ADR = IF1CMDMSK; // Point to Command Mask 1
262 1 CAN0DAT = 0x00b8; // Set to WRITE, and alter all Msg Obj except ID MASK
263 1
264 1 CAN0ADR = IF1ARB1; // Point to arbitration1 register
265 1 CAN0DAT = 0x0000; // Set arbitration1 ID to "0"
266 1 CAN0DAT = 0x8004; // and data bits
267 1 CAN0ADR = IF1ARB1; // Point to arbitration1 register标准桢
268 1 CAN0DAT = 0x0000; // Set arbitration1 ID to "0"
269 1 temp=id<<2;
270 1 temp&=0x1fff;
271 1 temp|=0x8000;
272 1 // Arb2 high byte:Set MsgVal bit, no extended ID,
273 1 // Dir = RECEIVE
274 1 CAN0DAT = temp; // Msg Cntrl: set RXIE, remote frame function disabled
275 1 CAN0DAT =0x0488;
276 1 CAN0ADR = IF1CMDRQST; // Point to Command Request reg.
277 1 CAN0DATL = MsgNum; // Select Msg Obj passed into function parameter list
278 1 // --initiates write to Msg Obj
279 1 // 3-6 CAN clock cycles to move IF register contents to the Msg Obj in CAN RAM
280 1 }
281
282 //Initialize Message Object for TX
283 /*void init_msg_object_TX (char MsgNum,unsigned int id)
284 { uint temp;
285 SFRPAGE = CAN0_PAGE;
286 CAN0ADR = IF1CMDMSK; // Point to Command Mask 1
287 CAN0DAT = 0x00B3; // Set to WRITE, & alter all Msg Obj except ID MASK bits
288 CAN0ADR = IF1ARB1; // Point to arbitration1 register
289 CAN0DAT = 0x0000; // Set arbitration1 ID to highest priority
290 temp=id<<2; // Autoincrement to Arb2 high byte:
291 temp&=0x1fff; // Set MsgVal bit, no extended ID, Dir = WRITE
292 temp|=0xa000;
293 CAN0DAT = temp; // Msg Cntrl: DLC = 1, remote frame function not enabled
294 CAN0DAT=0x0088;
295 CAN0ADR = IF1CMDRQST; // Point to Command Request reg.
296 CAN0DAT = MsgNum; // Select Msg Obj passed into function parameter list
297 // --initiates write to Msg Obj
298 // 3-6 CAN clock cycles to move IF reg contents to the Msg Obj in CAN RAM.
299 }
300 */
301 //Start CAN
302 void start_CAN (void)
303 {
C51 COMPILER V7.08 LCDC_040 04/24/2008 15:54:41 PAGE 6
304 1 /* Calculation of the CAN bit timing :
305 1
306 1 System clock f_sys = 22.1184 MHz/2 = 11.0592 MHz.
307 1 System clock period t_sys = 1/f_sys = 90.422454 ns.
308 1 CAN time quantum tq = t_sys (at BRP = 0)
309 1
310 1 Desired bit rate is 1 MBit/s, desired bit time is 1000 ns.
311 1 Actual bit time = 11 tq = 996.65ns ~ 1000 ns
312 1 Actual bit rate is 1.005381818 MBit/s = Desired bit rate+0.5381%
313 1
314 1 CAN bus length = 10 m, with 5 ns/m signal delay time.
315 1 Propagation delay time : 2*(transceiver loop delay + bus line delay) = 400 ns
316 1 (maximum loop delay between CAN nodes)
317 1
318 1 Prop_Seg = 5 tq = 452 ns ( >= 400 ns).
319 1 Sync_Seg = 1 tq
320 1
321 1 Phase_seg1 + Phase_Seg2 = (11-6) tq = 5 tq
322 1 Phase_seg1 <= Phase_Seg2, => Phase_seg1 = 2 tq and Phase_Seg2 = 3 tq
323 1 SJW = (min(Phase_Seg1, 4) tq = 2 tq
324 1
325 1 TSEG1 = (Prop_Seg + Phase_Seg1 - 1) = 6
326 1 TSEG2 = (Phase_Seg2 - 1) = 2
327 1 SJW_p = (SJW - 1) = 1
328 1
329 1 Bit Timing Register = BRP + SJW_p*0x0040 = TSEG1*0x0100 + TSEG2*0x1000 = 2640
330 1
331 1 Clock tolerance df :
332 1
333 1 A: df < min(Phase_Seg1, Phase_Seg2) / (2 * (13*bit_time - Phase_Seg2))
334 1 B: df < SJW / (20 * bit_time)
335 1
336 1 A: df < 2/(2*(13*11-3)) = 1/(141-3) = 1/138 = 0.7246%
337 1 B: df < 2/(20*11) = 1/110 = 0.9091%
338 1
339 1 Actual clock tolerance is 0.7246% - 0.5381% = 0.1865% (no problem for quartz)
340 1 */
341 1
342 1 SFRPAGE = CAN0_PAGE;
343 1 CAN0CN |= 0x41; // Configuration Change Enable CCE and INIT
344 1 CAN0ADR = BITREG ; // Point to Bit Timing register
345 1 CAN0DAT = 0x2640; // see above
346 1
347 1 CAN0ADR = IF1CMDMSK; // Point to Command Mask 1
348 1 CAN0DAT = 0x0087; // Config for TX : WRITE to CAN RAM, write data bytes,
349 1 // set TXrqst/NewDat, clr IntPnd
350 1
351 1 // RX-IF2 operation may interrupt TX-IF1 operation
352 1 CAN0ADR = IF2CMDMSK; // Point to Command Mask 2
353 1 CAN0DATL = 0x1F; // Config for RX : READ CAN RAM, read data bytes,
354 1 // clr NewDat and IntPnd
355 1 CAN0CN |= 0x06; // Global Int. Enable IE and SIE
356 1 CAN0CN &= ~0x41; // Clear CCE and INIT bits, starts CAN state machine
357 1
358 1
359 1 }
360
361 /*
362 void transmit(char MsgNum)
363 {
364 uchar num;
365 SFRPAGE=CAN0_PAGE;
C51 COMPILER V7.08 LCDC_040 04/24/2008 15:54:41 PAGE 7
366 CAN0ADR=IF1CMDMSK;
367 CAN0DAT=0x0087;
368 CAN0ADR=IF1DATA1;
369 for(num=0;num<8;num++)
370 {CAN0DATH=sdata[num];
371 num++;
372 CAN0DATL=sdata[num];
373 }
374 CAN0ADR=IF1CMDRQST;
375 CAN0DATL=MsgNum;
376 }
377
378
379 void receive_data(uchar MsgNum)
380 {
381 uchar i;
382 SFRPAGE=CAN0_PAGE;
383 CAN0ADR=IF2CMDMSK;
384 CAN0DATL=0x0f;
385 CAN0ADR=IF2CMDRQST;
386 CAN0DATL=MsgNum;
387 CAN0ADR=IF2DATA1;
388 for(i=0;i<8;i++)
389 {rdata[i]=CAN0DATL;
390 i++;
391 rdata[i]=CAN0DATH;
392 }
393 isnewdata=1;
394 }
395 */
396 void transmit(char MsgNum,char *p,char len)
397 {
398 1 char i;
399 1 SFRPAGE=CAN0_PAGE;
400 1 CAN0ADR=IF1CMDMSK;
401 1 CAN0DAT=0x0087;
402 1 CAN0ADR=IF1DATA1;
403 1 for(i=0;i<len;i+=2)
404 1 {CAN0DATH=*p++;
405 2 CAN0DATL=*p++;
406 2 }
407 1 CAN0ADR=IF1CMDRQST;
408 1 CAN0DATL=MsgNum;
409 1 }
410
411
412 void receive_data(uchar MsgNum,char *p,char len)
413 {
414 1 char i;
415 1 SFRPAGE=CAN0_PAGE;
416 1 CAN0ADR=IF2CMDMSK;
417 1 CAN0DATL=0x0f;
418 1 CAN0ADR=IF2CMDRQST;
419 1 CAN0DATL=MsgNum;
420 1 CAN0ADR=IF2DATA1;
421 1 for(i=0;i<len;i+=2)
422 1 {*p++=CAN0DATH;
423 2 *p++=CAN0DATL;
424 2 }
425 1 isnewdata=1;
426 1 }
427
C51 COMPILER V7.08 LCDC_040 04/24/2008 15:54:41 PAGE 8
428
429
430
431 ////////////////////////////////////////////////////////////////////////////////
432 //Interrupt Service Routine
433 ////////////////////////////////////////////////////////////////////////////////
434 void ISRname (void) interrupt 19
435 {
436 1 temppage=SFRPAGE;
437 1 SFRPAGE=CAN0_PAGE;
438 1 status = CAN0STA;
439 1 if ((status&0x10) != 0)
440 1 { // RxOk is set, interrupt caused by reception
441 2 CAN0STA &=0xef; // Reset RxOk, set LEC to NoChange
442 2 /* read message number from CAN INTREG */
443 2 receive_data (0x04,rdata,8); // Up to now, we have only one RX message
444 2 lcdtoken=1;
445 2 }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -