I looked in the manual (page 177) for the DE2 and as far as I understand it should be possible to do serial communication for instance via putty and a usb-to-serial cable to the board, so I take the program from the manual:
/* A simple program that recognizes the characters 't' and 'v' */
#include <stdio.h>
#include <string.h>
int main ()
{
char* msg = "Detected the character 't'.\n";
FILE* fp;
char prompt = 0;
fp = fopen ("/dev/uart1", "r+"); //Open file for reading and writing
if (fp)
{
while (prompt != 'v')
{ // Loop until we receive a 'v'.
prompt = getc(fp); // Get a character from the JTAG UART.
if (prompt == 't')
{ // Print a message if character is 't'.
fwrite (msg, strlen (msg), 1, fp);
}
if (ferror(fp))// Check if an error occurred with the file pointer
clearerr(fp); // If so, clear it.
}
fprintf(fp, "Closing the JTAG UART file handle.\n");
fclose (fp);
}
return 0;
}
And I try to run it as Nios2 hardware but then I get this message when I have configured std i/o to use uart
nios2-terminal: can't open uart: No such file or directory
And then when I connect with a terminal program (putty serial connection) it doesn't connect. What am I doing wrong? I tried in the propeties of the projet to change the std i/o to uart but that didn't help. Can you help me?
HOW TO DEBUG SERIAL COMMUNICATION:
Take your 9 pin serial cable and put a jumper pins 2 and 3 together. You can use a paperclip or whatever you have handy. Pins 2 and 3 are TX and RX. If you connect them together, any command you send from the computer will be received by the computer. You have created a serial loopback!
Open Putty, try to connect to your serial cable. Hit any key on your keyboard. Baud rate and things don't matter because it's a loopback.
If you see the character you sent out received on the terminal, your serial cable works! If not, you have a problem with your cable or with putty. I have had issues with putty in the past with serial communication. Try downloading Tera Term if you have a problem with Putty not connecting.
Or find new drivers for your serial cable! Good luck.
In Linux, I would do the following.
fp = fopen ("/dev/ttyS0", "r+"); //Open file for reading and writing
or
look for ttyS1; if ttyS0 is being used.
fp = fopen ("/dev/ttyS1", "r+"); //Open file for reading and writing
Do dmesg to know which exact device are you have attached.
$tail -f /var/log/messages
For USB-serial, it might be
/dev/ttyUSB0; the exact number can be find out using /var/log/messages
Related
Recently I've written a driver for a drawing tablet called the "Boogie Board RIP" to be able to use it as an input device for linux. It can be connected via usb to a computer. When the provided pen is near or touching the device's screen, it will send data telling where the pen is on the screen.
Basically the driver works great. I can write on it as if it was a wacom tablet.
At unpredictable times, the program will hang on the line below and the cursor on my computer screen will stay in place
fread(packet, sizeof(char), BYTES, f);
Where:
"packet" is an array of 8 bytes
"BYTES" is 8
"f" is a file opened in binary read (rb) mode. In my case it's /dev/usb/hiddev0
The basic program layout is a while loop that reads a byte at a time. Below is a mock-up of the much larger thing:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
int main(int argc, char *argv[]) {
char *path = argv[1];
unsigned char packet[8];
FILE *f = fopen(path, "rb");
int i;
while (1) {
fread(packet, sizeof(char), 8, f);
for(i=0;i<8;i++) {
printf("%x", packet[i]);
fflush(stdout);
}
}
}
I started to notice that my driver would "freeze" more often when I was running more things, like watching youtube, playing music... These aren't great examples. Basically I began to suspect it was related to CPU utilization. So I wrote the program below to test it:
#include <stdio.h>
int main() {
while(1) {
printf("a");
fflush(stdout);
fflush(stdout);
fflush(stdout);
fflush(stdout);
fflush(stdout);
fflush(stdout);
fflush(stdout);
}
}
Running this "infinite loop" program in a separate terminal while running the other program above in another terminal will result in harshly more frequent freezes. Basically the program will stop at the fread() line without fail within 2 seconds.
I learned that when the call to fread() doesn't get any data I can still read from the device with another instance of that program or simply printing out the contents of the file via sudo cat /dev/usb/hiddev0. The original process remains stuck while the new program will spit out the data coming from the device.
It seems as though the file simply closes. But that doesn't make sense because then fread would segfault on the next read. Looking for any ideas.
EDIT:
I solved this by using libusb to deal with reading from my device rather than trying to read directly from the device file.
I have a embedded device running Linux Angstrom. I need to detect a USB drive. So when a USB drive is inserted, I need to automatically copy data from the USB to internal memory of the embedded device.
To detect the USB, I am using below code:
DIR* dir = opendir("/media/sda1/");
if (dir)
{
printf("USB detected\n");
//rest of the code
//to copy data from the USB
}
This works normally but sometimes after copying is done, I remove the USB but the name of the mount point (sda1) remains there. So after removing the USB, it again try to copy the data (because sda1 is there in media) and then shows error because physical no USB is connected. What is the best way to detect if USB is connected and if connected then after copying how to eject it properly. Here I cannot use udisks because its not available for the linux angstrom I am using for this embedded device. So only generic linux commands will work.
Any help. Thanks
One naive approach is the following:
execute mount | grep /dev/sda1
parse the output: if there is no output, that means that sda1 is not mounted
You may have to adapt the code to your specific platform.
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
/* launch a command and gets its output */
FILE *f = popen("mount | grep /dev/sda1", "r");
if (NULL != f)
{
/* test if something has been outputed by
the command */
if (EOF == fgetc(f))
{
puts("/dev/sda1 is NOT mounted");
}
else
{
puts("/dev/sda1 is mounted");
}
/* close the command file */
pclose(f);
}
return 0;
}
I'm trying to change the keyboard driver in minix, my idea is store in a file all the characters that the used introduced in the keyboard.I declare a global FILE * fp and insert this piece of code in /usr/src/drivers/tty/keyboard.c
while (icount > 0) {
scode = *itail++; /* take one key scan code */
if (itail == ibuf + KB_IN_BYTES) itail = ibuf;
icount--;
/* Function keys are being used for debug dumps. */
if (func_key(scode)) continue;
/* Perform make/break processing. */
ch = make_break(scode);
if (ch <= 0xFF) {
/* A normal character. */
fp = fopen("log.txt","a+");
fprint(fp,"%c",ch);
fclose(fp);
buf[0] = ch;
(void) in_process(tp, buf, 1);
} else ...
then I run "make" in the directory and reboot but this does not work. I mean, the file is not created.
Any idea?
This won't work. The keyboard driver is inside the TTY "driver", a service which is in charge of the console. FS/VFS will transmit the I/O requests concerning that console to TTY. fopen, fprint, and fclose in your code are ways to perform such requests. But VFS can only handle requests from "user" programs (and transmit them down to drivers); TTY is not a "user" program, and as such, is not allowed to perform I/O requests.
I found a tutorial for writing data to an Arduino board over here: https://salilkapur.wordpress.com/2013/03/08/communicating-with-arduino-using-c/
The code uses file = fopen("/dev/ttyUSB0","w+");to open the port for the read/write operation and uses fprintf to write data to the device. But when I tried using fscanf to retrieve the data from the Arduino (I used Serial.print for writing the data back to the PC from the Arduino end, and the data was formatted as DEC), it didn't work.
I am able to see the output using the serial monitor in the Arduino IDE but I am not able to view the output in my C program's output. Why isn't it working and what do I have to do to get it working?
The program was run in Ubuntu.
This is my C code that is supposed to run on the PC:
#include <stdio.h>
int main()
{
FILE *file;
char a=0;
file = fopen("/dev/ttyUSB0","w+");
int i = 0;
if(file == -1)
printf("error");
for(i = 0 ; i < 3 ; i++)
{
fprintf(file,"C");
fscanf(file, "%c", &a);
printf("%c", a);
}
fclose(file);
}
I also tried few variations like, using %d instead of %c, using int in place of char and using fflush. I don't know why it doesn't work. Could it be that my Arduino board doesn't work?
Note: it is supposed to give an output after every character input.
The reason you cannot read anything is that when you call
file = fopen("/dev/ttyUSB0","w+");
the arduino is reset, and it takes 1-2 seconds to boot. For some reason, the read hangs indefinetely.
Adding sleep(2); next to fopen will likely do the trick.
See how to disable auto reset
I'm trying to read data from a COM port line-by-line in Windows. In PuTTY, the COM connection looks fine - my serial device (an MSP430 Launchpad) outputs the string "Data" once per second. However, when I use a simple C program to read the COM port and print out the number of bytes read, then the data itself, it gets completely mangled:
0
6 Data
2 Data
4 ta
6 Data
3 Data
3 a
a
6 Data
6 Data
2 Data
The lines saying 6 Data are correct (four characters, then \r\n), but what's happening to those lines that do not contain a complete message? According to the documentation, ReadFile should read an entire line by default. Is this incorrect - do I need to buffer it myself and wait for a linefeed character?
Note that not all those errors would occur in each run of the code; I did a few runs and compiled a variety of errors for your viewing pleasure. Here's the code I'm using:
#include <windows.h>
#include <stdio.h>
static DCB settings;
static HANDLE serial;
static char line[200];
static unsigned long read;
static unsigned int lineLength = sizeof(line) / sizeof(char);
int main(void) {
int i = 10;
serial = CreateFile("COM4",
GENERIC_READ | GENERIC_WRITE,
0, NULL,
OPEN_EXISTING,
0, NULL);
GetCommState(serial, &settings);
settings.BaudRate = CBR_9600;
settings.ByteSize = 8;
settings.Parity = NOPARITY;
settings.StopBits = ONESTOPBIT;
SetCommState(serial, &settings);
while(i) {
ReadFile(serial, &line, lineLength, &read, 0);
printf("%lu %s\n", read, line);
i--;
}
scanf("%c", &read);
return 0;
}
Compiled in Windows 7 64-bit using Visual Studio Express 2012.
What's happening is that the ReadFile is returning after it gets any data. Since data may come on a serial port at some point in the future, ReadFile will return when it gets some amount of data on the serial port. The same thing happens in Linux as well, if you attempt to read from a serial port. The data that you get back may or may not be an entire line, depending on how much information is in the buffer when your process gets dispatched again.
If you take another look at the documentation, notice that it will only return a line when the HANDLE is in console mode:
Characters can be read from the console input buffer by using ReadFile with a handle to console input. The console mode determines the exact behavior of the ReadFile function. By default, the console mode is ENABLE_LINE_INPUT, which indicates that ReadFile should read until it reaches a carriage return. If you press Ctrl+C, the call succeeds, but GetLastError returns ERROR_OPERATION_ABORTED. For more information, see CreateFile.