Sending value from kernel mode to user mode - driver

I'm developing a kernel-mode driver for an Anti Virus program, but I've a problem in Drivers section
I want to send a string value (For example "String") from Kernel-mode driver to user-mode application .
can anyone help me to do this ?

This question was asked a long ago, and I hope you have found the solution. I am posting this solution as there was none.
It depends on how you want to send the string to the user mode client application.
One way is IOCTL command. You issue a simple IOCTL command with METHOD_BUFFERED (assuming that string is little data) and voila, you are done.
Other way is to make client wait for an event, and make driver fire an event when that string is available to kernel driver. Then, as the wait in the user mode application is over, you will get the data. (of course, if wait didn't timed out or many other things)

There is function copy_to_user defined here
include/asm/uaccess.h. With help of it you can safely copy data from kernel mode to user mode.

Related

No telemetry trigger in TB

Is it possible to trigger an alarm when there is no telemetry from the device for a specified time or for a given number of polling periods?
This trigger has the same meaning as a Dead man's switch for humans.
Or what is the best way for TB to detect a broken connection, assuming that not every IoT device can keep an open TCP/MQTT/etc session for a long time.
Thingsboard's builtin rules engine may help you on this, Official Docs
BTW, there is a nice user guide to help you detect inactive/offline devices, see here

Gnuradio streaming between two computers?

Is there a simple way to implement communication between two computers running GNUradio using the standard blocks set?
What I am have now is this:
On a Linux computer, GNUradio is running and receiving input from a Radio peripheral. On that computer I can see the received waveform on a WX scope. I can also use sliders and input boxes to change things like the receiver frequency.
What I'd like to do is this:
On a Windows computer, I have the WX scope and sliders. When I move the a slider or change an input box, that data gets sent to the Linux, which is still running the radio receiver on Gnuradio. The received signal goes through a stream back to the windows, and gets displayed on the WX scope on Windows.
Someone elsewhere suggested using the ZMQ blocks, however, when I tried setting up a PUSH/PULL to transmit a sine wave from the Linux to the Windows, nothing went through. The guy who recommended that approach tried the same and also could not get it working, so I think that block might be broken?
So is there any alternative blocks that can do what I'm trying to do? Preferably something well documented, and available on GNUradio-companion.
Depending on the data rate from the receiver, it's possible to encounter performance issues attempting to send raw waveform data using e.g. the UDP blocks, where the sender may print an error similar to the following:
gr::log :WARN: udp_source0 - Too much data; dropping packet.
Because the scope widgets usually only display a portion of the input data, a more ideal way of remotely visualizing the waveform might be to only send the rendered scope widget (e.g. using a remote desktop such as VNC or X2Go). Although this solution reaches beyond your original problem, it is probably easier to use in the long run for cases involving two-way GUI interaction.
For the scope widget data, the UDP sink and source blocks seem to be native to GNU Radio, and are either sufficiently documented solution or simple enough for this problem, again taking firewall configuration into consideration as #Zephyr mentioned.
From GRC, specify in the UDP blocks:
the hostname or IP address of the display computer, and
a choose port number that isn't already in use (and were you using Linux, OS X, or anything UNIX-like, not any port below 1024).
For setting variables over the network, you might try the XMLRPC blocks, as described in another answer. These were recently deprecated, however.
See my other answer for discussion of alternative if performance issues arise.
Both Linux and Windows should have firewalls which might be blocking the connections.
You need to post the error messages displayed in gnuradio-companion.

Sending a UDP packet within a kernel module

Background: I'm a fourth year computer engineering major at UCSB. I've taken networking and operating systems courses. I created a program in userspace that broadcasts UDP packets onto the subnet and receives UDP packets in an adhoc network. What I'm trying to accomplish is to convert this program into a kernel module that will work on an ARM embedded system with Angstrom Linux, kernel version 2.6.39 (the x86 to ARM architecture cross compilation is an issue for another day). The reason for this move to the kernel is to shed some of the overhead of userspace functions and to make the sending and receiving part as quick as possible.
I've never done anything like this before in any of the courses I've taken, so please tell me if anything I am saying is incorrect, useless or inefficient!
After research with Google, I've concluded the typical way is to do away with sockets entirely and work with the sockbuf structure and fill in the necessary headers myself. Would this have an effect on the ability to broadcast packets on the subnet?
I am currently trying to follow the code here:
UDP packet send with linux-kernel module without using sockets
I've figured out the reasoning behind most of the code, but the last part is what confuses me:
eth = (struct ethhdr *) skb_push(skb, ETH_HLEN);
skb_reset_mac_header(skb);
skb->protocol = eth->h_proto = htons(ETH_P_IP);
memcpy(eth->h_source, dev->dev_addr, ETH_ALEN);
memcpy(eth->h_dest, remote_mac, ETH_ALEN);
skb->dev = dev;
dev_queue_xmit(skb);
All of the ethernet header seems to be constructed purely out of headers defined in the kernel besides the source MAC address, is this correct? I am going to be broadcasting my packets, so what exactly should be put into the destination MAC address field?
More importantly, what is dev in the skb->dev = dev; line? From my investigation, it is a pointer to the device driver it is associated with. From my understanding, I would want this to point to the wireless chip device driver as I am using 802.11 to communicate. Do I have to create my own dev struct for the wireless driver? If so, there any guidance on how to accomplish this? If not, how can I access the existing device driver and use this in a kernel module?
I've tried commenting out the dev line and running the code but unsurprisingly I get a kernel panic once it executes dev_queue_xmit(skb);.
Again, I've never done anything like this before, so any advice would be helpful, even if it means changing my approach entirely! I also understand that this could be a niche of a question, but any sort of guidance is appreciated!
Thank you in advance!
The best way is not to interfere with the protocol if you are not trying to modify one. Work on a higher (socket) layer. This API can be found in net/socket.c
This will help: (open in new browser tab/window to zoom)

how to : do 2 way communication between user mode and kernel mode

I have written a driver, that extracts a value from IRP buffer. Now based on this keyword I have to pass or discard the IRP. So I need to communicate with the database which is not easy from kernel mode driver. So I am using an application or exe for doing this which will result in true or false based on which I will pass or discard the IRP.
I want to link the driver with the application that I get the data in the client application.
I thought about using temp file that can act as a pipe.
Please suggest something.
I would go with IOCTLs.
The application communicating with database starts with sending one or more IOCTLs to the driver. Let's call IOCTLs of this type IOCTL-1.
The completion of IOCTL-1 idicates a request from driver to the database. The request details can be passed in IOCTL output buffer.
The application detects IOCTL-1 completion, retrieves the request details, runs the query and passes results to the driver using a different IOCTL (IOCTL-2). Then it re-sends IOCTL-1 so that the driver can issue another request.

Windows UPS (Uninterruptible Power Supply) service - turn off UPS?

I'm using the UPS service to monitor the state of my UPS from an application -- the key at HKLM\SYSTEM\CCS\Services\UPS\Status has all the information you can get from the Power control panel. BUT -- I'd like to be able to tell the UPS to shut down from my app as well. I know that the service can tell the UPS to shut down -- for instance, after running a set number of minutes on battery -- and I'm wondering if there's some kind of command I can send to the service to initiate a shutdown manually.
I'm having trouble searching for this information -- people tend to misspell "Uninterruptible" (hrm, Firefox red-lined that but doesn't have an alternative) and "UPS" just gets hits for the shipping service. Maybe I can do something through System.ServiceController, or WMI?
CLARIFICATION: Yes, I am talking about powering down the physical UPS device. I know how to stop the service. I figured it would be a common problem -- I want my UPS to turn off with the PC. I had an idea I'm going to try, based on this page. You see, APC (and everybody else) has to supply a DLL for the UPS service to call, and since the function calls are well documented, there's no reason I shouldn't be able to P/Invoke them. I'll re-edit this once I know whether or not it worked.
Update: I tried invoking UPSInit, then UPSTurnOff, and nothing happens. I'll tinker with it some more, but the direct call to apcups.dll might be a dead end.
Check my comments to Herman, you want to shut the UPS down, not the UPS SERVICE, correct? I mean, you want that thing to shut off, kill the power, etc, right?
If so, you are looking it on a UPS by UPS model. I doubt two of them would work the same.
In your searches, instead of UPS, try "APC", or "battery". I think a lot of the code is what runs on laptops to deal with being on battery, etc...
Some place hidden in some dusty old files I have protocol information for APC UPS's, and the commands they respond to, and what they send to the PC etc. But this was WAY back in the day when we used to connect our UPS's to our computers with SERIAL cables... You could actually talk to a UPS with Qmodem or Hyperterm...
Learned it from talking to the guys at APC. They are very nice, and helpful. Now-a-days, I think you just post a URL coming from your Powerchute software, and it will talk directly to the UPS, and carry out your commands.
OK, I have the answer (tested!), but it's not pretty. My APC UPS communicates using the APC "Smart" protocol (more here). What you need in my case is a "soft shutdown", "S" command. But first you need to make sure it's in "Smart" mode ("Y"). Now, if you want to let the Windows UPS service monitor state, the service will have an iron grip on the COM port. So you can either a) let the Windows service turn the UPS off, or b) kill the service and turn the UPS off yourself.
The UPS itself has a "grace period" after it gets the "S" command, giving you time to shut down your OS. This means that to do (a) above, you have to:
Kill utility (mains) power
Wait for the Windows UPS Service timeout (default and minimum 2 minutes)
Wait for Windows to shut down -- right near the end, it will send the "S" command
Wait for the UPS grace period, after which it will actually turn itself off
I think we're going to opt for (a), just because (b) involves extra work killing the service and implementing the serial comms.
Please, tell in what language are you trying to do that... if you're using .NET you can do that with ServiceController class (read the docs).
For controlling services in Win32 API using C/C++, Service Functions (Windows).
For example to stop a service you can use ControlService function as follows (this is a quick and dirty example):
OpenService (hServMgr, TEXT("\\UPS_SERVICE_0"), SC_MANAGER_ALL_ACCESS);
SERVICE_STATUS stat;
ControlService (hUpsService, SERVICE_CONTROL_STOP, &stat)
Note that you need to provide a Service Manager handle in hServMgr and the \\UPS_SERVICE_0 name is the name that must match with your desired UPS service (either the Windows built-in or another).
Remember that to stop a service you need the proper security rights. This is not a problem with an Adminstration account, but keep in mind what happens when logging with a non-admin account.
Hope that helps.
About shutting down the physical UPS device, I remember back in WIn98 days I was able to poweroff the device talking with the UPS through the COM port, altough I don't remember the brand or how the programming interface was.

Resources