Log in

View Full Version : problems assigning unsigned chars in FRC Code


LoyolaCubs
24-01-2004, 18:03
Whenever I assign variables (including competition_mode, autonomous_mode, pwm01, and pwm02), the variable values turn into 256x whatever I assigned. :ahh: For instance, if I give pwm01 the value 127, the value returned after I use a printf command is 32512. Here is my code in my Stop function (located in the User_Autonomous_Code function):

void Stop (int counter1) // Drive forward until counter reaches zero
{
while( counter1 > 0 )
{
counter1--;
pwm01 = 127;
printf("pwm01: %d\n", pwm01);
pwm02 = 127;
printf("pwm02: %d\n", pwm02);
printf("should be stopped \n");
printf("counter1: %d\n", counter1);
}
}

Anyone have a similar problem or know how to fix it?

Jay Lundy
24-01-2004, 18:09
Cast everything to int before printing. The reason is that printf assumes your variable is an int, and it reads from MSB to LSB.

So if you have a char with value 127 (01111111), then printf will start on the far left, and create an int that looks like 01111111 00000000. Everything is shifted up 8 bits, << 8 = * 2^8 = * 256.

If you cast to int first, the variable is padded with 0's, so 01111111 becomes 00000000 01111111.

By the way, I didn't look at the implementation to see why printf works this way. This is just what I'm assuming based on the problem (it's a common problem).

Mark McLeod
24-01-2004, 18:10
Whenever I assign variables (including competition_mode, autonomous_mode, pwm01, and pwm02), the variable values turn into 256x whatever I assigned. :ahh: For instance, if I give pwm01 the value 127, the value returned after I use a printf command is 32512. Here is my code in my Stop function (located in the User_Autonomous_Code function):

void Stop (int counter1) // Drive forward until counter reaches zero
{
while( counter1 > 0 )
{
counter1--;
pwm01 = 127;
printf("pwm01: %d\n", pwm01);
pwm02 = 127;
printf("pwm02: %d\n", pwm02);
printf("should be stopped \n");
printf("counter1: %d\n", counter1);
}
}

Anyone have a similar problem or know how to fix it?

The problem is in your use of printf.
printf always assumes it is printing a signed integer.


Change it to:

void Stop (int counter1) // Drive forward until counter reaches zero
{
while( counter1 > 0 )
{
counter1--;
pwm01 = 127;
printf("pwm01: %d\n", (int) pwm01);
pwm02 = 127;
printf("pwm02: %d\n", (int) pwm02);
printf("should be stopped \n");
printf("counter1: %d\n", (int) counter1);
}
}

LoyolaCubs
24-01-2004, 18:30
Thanks for your help. Now the printf is coming out correctly. However, the motors are not running properly. Our Drive_Forward command looks like this:

void Drive_Forward(int counter1) // Drive forward until counter reaches zero
{
while( counter > 0 )
{
counter--;
p1_y = 254;
printf("pwm01: %d\n", (int) p1_y);
p2_y = 254;
printf("pwm02: %d\n", (int) p2_y);
printf("counter1: %d\n", counter1);
}
}

We are using the default code. The only change we've made is that the autonomous_code variable is set to 1. We called Drive_Forward(100) in the user_routines_fast loop.

Jay Lundy
24-01-2004, 18:37
p1_y is the input from the joystick port 1 y-axis. Changing p1_y isn't necessarily going to change pwm01 (depends on what other code you have).

Rather that setting p1_y and p2_y, try setting pwm01 and pwm02.

[Edit]
By the way, pwm01 is the output sent to pwm 1 when putdata() is called. It's not like last year where, by default, p1_y was the variable that both held the input from the joystick and was the output for pwm 1. This year we have more room for variables so now there is a seperate variable for input from joystick and output to pwm.

Mark McLeod
26-01-2004, 10:54
Thanks for your help. Now the printf is coming out correctly. However, the motors are not running properly. Our Drive_Forward command looks like this:

void Drive_Forward(int counter1) // Drive forward until counter reaches zero
{
while( counter > 0 )
{
counter--;
p1_y = 254;
printf("pwm01: %d\n", (int) p1_y);
p2_y = 254;
printf("pwm02: %d\n", (int) p2_y);
printf("counter1: %d\n", counter1);
}
}

We are using the default code. The only change we've made is that the autonomous_code variable is set to 1. We called Drive_Forward(100) in the user_routines_fast loop.

ditto what Jay said.
Also your code has a simple error.
You are passing in "counter1", but use "counter" (without the "1") in the routine.


Yep, the loop prevents the PWM values from being passed to the Master processor. You're just talking to yourself. ;)

LoyolaCubs
26-01-2004, 23:21
Thanks all for your help. I got the autonomous dead reckoning working. Now I better move on to the harder stuff...

Btw, I learned that while loops in the Drive_Forward function are a bad idea. The counter should really be added to in the main loop that takes 26.2 ms. If you throw a while loop in the Drive_Forward function, the loop can take too long and anger the main program. Therefore, we have something like this:

void Drive_Forward()
{
pwm01 = 254;
pwm02 = 254;
}

Then down in the main loop:

{//loopy part
...
counter++;

if( counter < 100 && counter >= 50 )
{
Drive_Forward();
}
...
}

Eventually, we will use a timer rather than a counter to time movements. This is one reason C is so much more powerful than PBASIC. Anyway, I hope this lesson we learned helps you.