This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

serial port and timer

Hi,

I have a problem.I must send through the serial port the number 1 and the number 0 every second using a timer of the c167cs. Would someone know me to help?

  • Do you know how to use the C167's serial port?

    Do you know how to use a timer on the C167?

  • No unfortunately no. I have never used a Microcontroller. This problem has been assigned me and I doesn't know whether to resolve it. Could you help me?

  • Have you ever done any programming at all?

  • Here is an extremely basic program that does what you ask. Perhaps this helps to get you started as you will surely need to modify it.

    #include "c167cs.h"
    #include "intrins.h"
    
    void GPT1_viTmr3(void) interrupt 0x23 {
      S0TBUF = '0';
      S0TBUF = '1';  /* allowed since the register is double buffered */
      P2 ^= 0x0001;  /* toggle P2.0 */
    }
    
    void main(void) {
      /* setup the serial port */
      S0BG  = 0x0040; /* 9.600 kbaud @ 20 MHz clock */
      S0CON = 0x0011; /* format: 8-N-1 */
    
      /* P3.10 is used for TxD and P3.11 is used for RxD */
      _bfld_( P3,0x0C00,0x0400);    /**/
      _bfld_(DP3,0x0C00,0x0400);    /* set data direction */
    
      S0CON |= 0x8000; /* enable baud rate */
    
      /* use GPT1 for the 1 second time base */
      T3CON = 0x0087;  /* clock tick is 51.2 usec, count down */
      T3    = 0x4C4B;  /* 1 second load value */
    
      T2CON = 0x0027;  /* t2 reloads T3 on the interrupt */
      T2    = 0x4C4B;
    
      T3IC  = 0x004B;  /* set up the interrupt level and enable it */
      T3R   = 1;       /* start timer 3 running */
    
      DP2   = 1;       /* toggle P2.0 every second */
    
      IEN   = 1;       /* globally enable interrupts */
    
      for(;;){};
    }
    

    Hope this helps.
    -Chris

  • Thanks a lot. Monday I will try it to the university and I will make you know. Thanks still for the help!

  • The code works very well and visualizes me "01" every second. As I do for making me visualize before "0", after a second "1", after another second "0", after another second "1" ..... etc. Must I put another timer? What must I change in the list? Thanks as for the help.

  • If I were to do it, I could imagine that you would use a counter (volatile variable) that checks if it is even or odd. If even you send a '0' and when it is odd you send a '1'. This logic (code) would be placed in the interrupt that already exists for the one second.

  • "...I will try it to the university..."

    Is this a homework assignment that you should be doing yourself...?

  • In practice I must bring my thesis stand-alone using this microcontroller and the prof has told me to begin with this application.

  • The have inserted to "if" in such way to make me stamp, alternatively, "0" and "1" to distance of to second. The tails is the following:

    #include "c167cs.h"
    #include "intrins.h"
    
    int a;
    a=0;
    
    void GPT1_viTmr3(void) interrupt 0x23 {
    
      if(a=0)
         {S0TBUF = '0';
          a=1;}
      else
         {S0TBUF = '1';
          a=0;}
    
      P2 ^= 0x0001;  /* toggle P2.0 */
    }
    
    void main(void) {
      /* setup the serial port */
      S0BG  = 0x0040; /* 9.600 kbaud @ 20 MHz clock */
      S0CON = 0x0011; /* format: 8-N-1 */
    
      /* P3.10 is used for TxD and P3.11 is used for RxD */
      _bfld_( P3,0x0C00,0x0400);    /**/
      _bfld_(DP3,0x0C00,0x0400);    /* set data direction */
    
      S0CON |= 0x8000; /* enable baud rate */
    
      /* use GPT1 for the 1 second time base */
      T3CON = 0x0087;  /* clock tick is 51.2 usec, count down */
      T3    = 0x4C4B;  /* 1 second load value */
    
      T2CON = 0x0027;  /* t2 reloads T3 on the interrupt */
      T2    = 0x4C4B;
    
      T3IC  = 0x004B;  /* set up the interrupt level and enable it */
      T3R   = 1;       /* start timer 3 running */
    
      DP2   = 1;       /* toggle P2.0 every second */
    
      IEN   = 1;       /* globally enable interrupts */
    
      for(;;){};
    }
    

    The problem is that it stamps only me "1" every second. would someone know me to explain because? Thanks so much.

  • if (a = 0) { ... }
    

    is an assignment, i.e. it doesn't matter what value a had before your test. You must use == to compare, i.e.

    if (a == 0) { ... }
    

    Or reverse the two parts of the if/else and drop the explicit comparison:

    if (a) {
        S0TBUF = '1';
        a = 0;
    } else {
        S0TBUF = '0';
        a = 1;
    }
    

    You can also remove the if statement totally:

    S0TBUF = '0' + (a++ & 1);
    


    This extracts the odd/even bit of a, and continuously increments a.

  • The problem is that I want to stamp "0" then after a second "1", after another second "0", after another second "1" .... ect.With the instruction:

    S0TBUF = '0' + (a++ & 1);
    

    does it increase the value progressively?

  • "does it increase the value progressively?"

    Per's post clearly described what it does - read it again, carefully...

  • As I already mentioned: "This extracts the odd/even bit of a". This means you will alternate between adding 0 and 1 to your printout, i.e. the printout will be 0101010101010101010101...

    By the way - why do you want such a printout? It isn't exactly meaningful. You already have a toggling pin. Why emit trace output whenever you toggle the pin? Doesn't your pin toggling work?

  • Another thing: Why do you declare a as int? You are programming an 8-bit processor and int is in this case a 16-bit data type. Using a data type larger than the native register size is not recommended unless you need the range. In this case, your code only makes use of the values 0 and 1. You could use a 1-byte variable, or you could even modify your code to use a 1-bit variable.