2

For my assignment I need to read some strings coming from a serial port. This has to be done in a kernel module, so I can't use stdio library. I'm trying in this way:

#include <linux/module.h>
#include <linux/unistd.h>
#include <asm/io.h>
#include <asm/fcntl.h>
#define SERIAL_PORT "/dev/ttyACM0"

void myfun(void){
  int fd = open(SERIAL_PORT,O_RDONLY | O_NOCTTY);
  ..reading...

}

but it gives me "implicit declaration of function open"

0

3 Answers 3

2

You want to use the filp_open() function, it is pretty much a helper to open a file in kernelspace. You can find the man on it here

The file pointer from filp_open() is of type struct file and don't forget to close it with filp_close() when you're done:

#include <linux/fs.h>
//other includes...

//other code...    

struct file *filp = filp_open("/dev/ttyS0");
//do serial stuff...
filp_close(filp);
Sign up to request clarification or add additional context in comments.

5 Comments

@user1610075 - Did you include the right header file? (see edit above)
Ok now it works...anyway in the man it says something like it is not recommendend...moreover I found a reading example here howtoforge.com/… and seems pretty tricky to me, are you sure it is a good way to read from kernel space?
@user1610075 - it's not saying filp_open is not recommended, it's saying opening a file from the kernel is not recommended. But if you have to, this, or a mechanism based off of this, is the correct way (to the best of my knowledge).
Ah ok thanks! Listen I would need a non-blocking version of read, but I can't find any documentation...could you help me please?
That's kind of off topic, you should probably open a new question. But briefly, you could open with the O_NONBLOCK flag, or set this in fcntl, or use select() with NULL for timeouts
1

Finding your way around the kernel source can be pretty frightening since it's so large. Here's my favorite command: find . -iname "*.[chs]" -print0 | xargs -0 grep -i "<search term>.

A quick description:

  • find (obvious)
  • dot is the root directory of the kernel
  • iname is find the name ignoring case
  • .c .h and .s files contain code - look in them
  • print0 prints them out null terminated as they are found
  • xargs takes an input and uses it as an argument to another command (-0 is to use null terminated)
  • grep - search for string (ignoring case).

So for this search: "int open(" and you'll get some hits with tty in the name (those will be for consoles) - have a look at the code and see if they are what you want.

2 Comments

You can do the same with grep solely: grep -i -R --include="*.[chs]" "<search term>" .
I like my version better still because I can use it for things other than grep (perl expressions to replace found terms is a good example). But thanks for the tip (it can also be done with just find and --exec ... but xargs is faster)
-2

Include the header file for open, usually #include <unistd.h>

Edit:

Not sure about kernel use, but do a man 2 open.

On my version of linux you might need all following:

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>

depending on the macros you are using.

2 Comments

gives me "no existent"...maybe because I'm in a kernel module?
@user1610075 - Exactly. unistd.h is a part of glibc, that's not included in the kernel. The kernel has its own version of this linux/unistd.h

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.