UMDF PnP Driver creates no trace logs - umdf

Im trying to create trace log messages for this Idd Sample Driver. I am following this document.
I add WPP_INIT_TRACING(pDriverObject, pRegistryPath) to the DriverEntry, and WPP_CLEANUP(pDriverObject)to the EvtCleanupCallback.
_Use_decl_annotations_
void DriverContextCleanup(WDFOBJECT DriverObject)
{
UNREFERENCED_PARAMETER(DriverObject);
DoTraceMessage(MYDRIVER_ALL_INFO, "Tracing Fini Success");
WPP_CLEANUP(WdfDriverWdmGetDriverObject(DriverObject));
}
_Use_decl_annotations_
extern "C" NTSTATUS DriverEntry(
PDRIVER_OBJECT pDriverObject,
PUNICODE_STRING pRegistryPath
)
{
WDF_DRIVER_CONFIG Config;
NTSTATUS Status;
WDF_OBJECT_ATTRIBUTES Attributes;
WDF_OBJECT_ATTRIBUTES_INIT(&Attributes);
Attributes.EvtCleanupCallback = DriverContextCleanup;
WDF_DRIVER_CONFIG_INIT(&Config,
IddSampleDeviceAdd
);
WPP_INIT_TRACING(pDriverObject, pRegistryPath);
DoTraceMessage(MYDRIVER_ALL_INFO, "Tracing Init . . .");
Status = WdfDriverCreate(pDriverObject, pRegistryPath, &Attributes, &Config, WDF_NO_HANDLE);
if (!NT_SUCCESS(Status))
{
DoTraceMessage(MYDRIVER_ALL_INFO, "Tracing Init Failed");
WPP_CLEANUP(pDriverObject);
return Status;
}
DoTraceMessage(MYDRIVER_ALL_INFO, "Tracing Init Success");
return Status;
}
I add some DoTraceMessage() calls with a flag of MYDRIVER_ALL_INFO to the DriverEntry and DeviceEntry.
NTSTATUS IddSampleDeviceD0Entry(WDFDEVICE Device, WDF_POWER_DEVICE_STATE PreviousState)
{
UNREFERENCED_PARAMETER(PreviousState);
// This function is called by WDF to start the device in the fully-on power state.
DoTraceMessage(MYDRIVER_ALL_INFO, "Tracing Device Entry");
auto* pContext = WdfObjectGet_IndirectDeviceContextWrapper(Device);
pContext->pContext->InitAdapter();
return STATUS_SUCCESS;
}
I make sure WPP Tracing is set to YES in the properties of the project.
The project builds, I go into TraceView and open the IddSampleDriver.PDB file, I set the level to verbose, and check all of the flags. I verified that it has the trace stuff it needs. Since if I open the IddSampleApp.PDB file, it fails.
I install the driver after enabling TestSigning and installing with pnputil -a ./x64/Debug/IddSampleDriver/IddSampleDriver.inf, run the sample app, the driver spins up 3 virtual monitors in the Display Settings. I then exit the app, and the monitors disappear. Everything seems to be functional. The problem is there is no traces in TraceView.
I have tried using tracelog, following this. Still nothing.
I have tried using logman, following this. Still nothing.
I am at my wits end. I spent all last week on this, Trying every possible avenue to get my trace messages to appear.
Either I followed every one of these instructions with no success. Either I somehow messed up every single one of them, or I am missing something else that I need to do in order to view these traces.
Additional Info:
Trace.h was left untouched
Targeting x64, Debug. Running on build machine. Win10.
CTL file I used:
b254994f-46e6-4718-80a0-0a3aa50d6ce4 MyDriver1TraceGuid
Basic process I used (tracelog as example):
tracepdb -f .\x64\Debug\IddSampleDriver.pdb
tracelog -start TestTraceIDD -guid .\guid.ctl -f testTrace.etl -flag 0xff
pnputil -a .\x64\Debug\IddSampleDriver\IddSampleDriver.inf #install driver
.\x64\Debug\IddSampleApp.exe #create software device and attach driver to it
<exit app>
tracelog -stop TestTraceIDD
tracefmt.exe .\testTrace.etl -p . -o test.out```
pnputil -d oem20.inf -f #uninstall driver

Solved my problem. I wasnt actually installing my driver, since it was still installed from the first time I installed it, so it was always using that driver instead of my new one with WPP enabled. I was installing and uninstalling the driver with pnputil.
I was doing pnputil -d oem20.inf -f for example to uninstall the driver. This is BAD. I have learned now that force deleting a driver does nothing. The reason I was force deleting was because it wouldnt delete when i still had a device, even though i would exit the sample app.
So what you have to do in order to properly delete the driver is enumerate the devices with pnputil, remove the ones that use your driver, then delete the driver. This allows a proper fresh driver installation.

Related

Why am I getting "java.lang.NoClassDefFoundError: Could not initialize class io.mockk.impl.JvmMockKGateway" when using quarkusDev task in IntelliJ?

I am using Gradle 7.5, Quarkus 2.12.3 and mockk 1.13.3. When I try to run quarkusDev task from command line and then start continuous testing (by pressing r), then all tests pass OK.
However, when I do the same as from IntelliJ (as gradle run configuration), all tests fail with error:
java.lang.NoClassDefFoundError: Could not initialize class io.mockk.impl.JvmMockKGateway
How can I fix that?
Masked thrown exception
After much debugging I found the problem. The thrown exception actually originates in HotSpotVirtualMachine.java and is thrown during attachment of ByteBuddy as a java agent. Here is the relevant code;
// The tool should be a different VM to the target. This check will
// eventually be enforced by the target VM.
if (!ALLOW_ATTACH_SELF && (pid == 0 || pid == CURRENT_PID)) {
throw new IOException("Can not attach to current VM");
}
Turning check off
So the check can be turned off by setting ALLOW_ATTACH_SELF constant to true. The constant is set from a system property named jdk.attach.allowAttachSelf:
String s = VM.getSavedProperty("jdk.attach.allowAttachSelf");
ALLOW_ATTACH_SELF = "".equals(s) || Boolean.parseBoolean(s);
So, in my case, I simply added the following JVM argument to my gradle file and tests started to pass:
tasks.quarkusDev {
jvmArgs += "-Djdk.attach.allowAttachSelf"
}

At which address is qemu expecting to find the image?

I'm working with the qemu riscv32 emulator. I have managed to boot a simple hello-world image I have got from github, however I haven't managed to boot my own image. I suspect this is because I built my image without a linker script, therefore it is being loaded at the wrong address. I'm trying to understand how the qemu boot sequence works to fix this.
This is the linker script I'm using
OUTPUT_ARCH( "riscv" )
OUTPUT_FORMAT("elf32-littleriscv")
ENTRY( _start )
SECTIONS
{
/* text: test code section */
. = 0x20400000;
.text : { *(.text) }
/* gnu_build_id: readonly build identifier */
.gnu_build_id : { *(.note.gnu.build-id) }
/* rodata: readonly data segment */
.rodata : { *(.rodata) }
/* data: Initialized data segment */
. = 0x80000000;
.data : { *(.data) }
.sdata : { *(.sdata) }
.debug : { *(.debug) }
. += 0x1000;
stack_top = .;
/* End of uninitalized data segement */
_end = .;
}
And this is the qemu command I'm executing:
qemu-system-riscv32 -nographic -machine sifive_e -bios none -kernel hello
# with -s -S when debugging
The source code is not very relevant, it is just a small assembly file that writes "hello".
My main question is:
How can I know at which address is qemu expecting to find the image?
Other questions I would like to answer:
With gdb, I have noticed that qemu starts executing at address 0x1004 (before me doing anything). I was expecting it to be 0x0. Why is this?
I have read hat qemu can use U-boot. Does it use it, or any other bootloader, by default?
If so, is there any way to load an image at address 0x0 without any sort of bootloader intervening? (I ask this for debugging purposes, because the first time you try a new arch. possibly yo want to keep everything as simple as possible)
Does the kernel option just load the provided image, or does it something more? (like loading a Linux kernel and execute the provided image on top of it)
I'm using the sifive_e emulator, therefore I have gone to the SiFive E series datasheet (like this one ) to check the memory map, and find the starting address. This is what I have found:
Those address are very different from those specified in the linker script above. It seems I'm looking at the wrong place, where can I found the SiFive E boot address?
EDIT
With regards to the last question about the memory map, I found the answer. It is explained here (5.16) and here (chapter 6)

debugging vxworks loadModule failure

I have a VxWorks Image Project project without a File-System on MPC5200B, using DIAB tool-chain.
I need to dynamically load a module from flash.
I allocated memory on my stack char myTemporaryModuleData[MAX_MODULE_SIZE]
and filled it with the module data from Flash.
(checked that the binary data is intact)
then i create a memDevice('/mem/mem01', myTemporaryModuleData, moduleReadLength)
open the psuedo-stream int fdModuleData = open("/mem/mem01", O_RDONLY, 777);
when i run int mId = loadModule(fdModuleData, LOAD_ALL_SYMBOLS);
did not see anything in the console after running loadModule();
but mId = 0 which indicates failure :(.
getErrno() returned 0x3D0004 (S_objLib_OBJ_TIMEOUT)
NOTE: it didn't take long at all to fail => timeout?
i tried replacing the module with a simple void foo() { printf(...); } module but still failes with same issue.
tried loading an .out instead of .o
unfortunately, nothing got me nowhere,
How can i know what caused it to fail? (log, last_error, anything i should check?)
FOUND IT.
Apparently, it was a mistake in the data read from the flash.
What I can contribute is that 'loadModule()' from memDrv device is possible and working.

running multi-platform from an external java application

I am posting this after visiting all possibly related posts to my issue and could not find an exact solution.
I employing Jade in my master degree research project. That is, I would like to create several platforms from an external java application. by revising all documents in the website especially "administration" one, this would be similar to the scenario of launching several platforms using Command-line in Windows environment as the following using windows :
First platform
open a CMD
type : java jade.Boot -gui -platform-id Platform1
this will initiate a platform named Platform1, in which, its AMS would be reached in this address AMS#Platform1
Second platform
open a "new" another CMD
type : java jade.Boot -gui -platform-id Platform2 -local-port 1111
this will initiate a platform named Platform2, in which , its AMS would be reached in this address AMS#Platform2
and so on.
now this would work perfectly using the command line, as we can see different platforms with different IDs and ports can be launched such that Agents that live in them can communicate with other agents in the same platform or in remote platform.
however, I tried doing the same launching using external java application and could not succeed in doing so.
it only succeed in initiating the first platform, but it would not in the rest platforms.
this is my code
###############################################################
Profile p1 = new ProfileImpl(true);
p1.setParameter(ProfileImpl.PLATFORM_ID, "platform"+ID); // ID range from 1 to 10
p1.setParameter(Profile.LOCAL_PORT, Integer.toString(port)); // available port
Runtime.instance().setCloseVM(true)
ContainerController mc = Runtime.instance().createMainContainer(p1); // I need to have a main container for each platform
###############################################################
then I get this error
##############################################################
Aug 03, 2014 9:42:26 PM jade.imtp.leap.LEAPIMTPManager initialize
INFO: Listening for intra-platform commands on address:
- jicp://10.1.1.5:1024
- jicp://10.1.1.5:1025
Aug 03, 2014 9:42:26 PM jade.core.AgentContainerImpl joinPlatform
SEVERE: Some problem occurred while joining agent platform.
jade.core.ProfileException: Can't get a proxy to the Platform Manager - Caused by: Wrong platform name platform1. It should be platform2
at jade.core.ProfileImpl.createPlatformManager(ProfileImpl.java:529)
at jade.core.ProfileImpl.getPlatformManager(ProfileImpl.java:442)
at jade.core.ProfileImpl.getServiceManager(ProfileImpl.java:456)
at jade.core.AgentContainerImpl.init(AgentContainerImpl.java:346)
at jade.core.AgentContainerImpl.joinPlatform(AgentContainerImpl.java:492)
at jade.core.Runtime.createMainContainer(Runtime.java:166)
at intiator.intiatePlatform(intiator.java:49)
at MainLauncher.main(MainLauncher.java:69)
Nested Exception:
jade.core.IMTPException: Wrong platform name platform1. It should be platform2
at jade.imtp.leap.CommandDispatcher.setPlatformManager(CommandDispatcher.java:231)
at jade.imtp.leap.CommandDispatcher.registerSkeleton(CommandDispatcher.java:736)
at jade.imtp.leap.LEAPIMTPManager.exportPlatformManager(LEAPIMTPManager.java:198)
at jade.core.ProfileImpl.createPlatformManager(ProfileImpl.java:518)
at jade.core.ProfileImpl.getPlatformManager(ProfileImpl.java:442)
at jade.core.ProfileImpl.getServiceManager(ProfileImpl.java:456)
at jade.core.AgentContainerImpl.init(AgentContainerImpl.java:346)
at jade.core.AgentContainerImpl.joinPlatform(AgentContainerImpl.java:492)
at jade.core.Runtime.createMainContainer(Runtime.java:166)
at intiator.intiatePlatform(intiator.java:49)
at MainLauncher.main(MainLauncher.java:69)
Exception in thread "main" java.lang.NullPointerException
at intiator.intiatePlatform(intiator.java:58)
at MainLauncher.main(MainLauncher.java:69)
###############################################################
So I would like to make it successfully using code as it would be using Command-line
What you are suggesting is to create and launch two or more jade platforms in the same java program at once. This can not be possible unless you write a program that starts a single platform and increments the port and run it several time (as much as you need platforms). Otherwise I do not see any other option.
You can use this method to test if a port is available or not:
private boolean isAvailablePort(int port) {
ServerSocket ss = null;
DatagramSocket ds = null;
try {
ss = new ServerSocket(port);
ss.setReuseAddress(true);
ds = new DatagramSocket(port);
ds.setReuseAddress(true);
return true;
} catch (IOException e) {
} finally {
if (ds != null) {
ds.close();
}
if (ss != null) {
try {
ss.close();
} catch (IOException e) {
}
}
}
return false;
}
Then you can use this for example:
while(!isAvailablePort(port)){
port++;
}
to automate port incrementation.

atmel sensor using printf

I have an atmel UC3-L0 and compass sensor. Now I install AtmelStudio and download some demo code into the board. But I have no idea where the function printf in demo code will appear the data. How should I do to get the data?
The printf function outputs to stdout.
Usually on a "naked" processor with no operating system you need to define how a character is sent or received from a physical interface (usually an USART, console port, USB port, 4-port LCD interface, etc.). So typically you may want to use the USART port of your processor board to connect to a PC running Hyperterm, PuTTY or similar using a serial cable.
In essence you will need to
create FILE streams using the fdev_setup_stream() macro and
provide pointers to functions get() and put() that tell the printf() function how exactly to read and write from/to that stream (e.g. read/write to a USART, an LCD display, etc.).
you may have libraries - depending on your hardware - that already contain such functions (plus the correct port initialisation functions), like e.g. uart.c/.h, lcd.c/.h, etc.
In the documentation of stdio.h (e.g. here) look for the following:
printf(), fdev_setup_stream()
If you have downloaded Atmel Studio you may look into the stdiodemo.c code for further insight.
In order to use printf in ATMEL studio you should check the following things:
Add and Apply the Standard serial I/O module from Project->ASF Wizard.
Also add the USART module from the ASF Wizard.
Include the following code snippet before the main function.
static struct usart_module usart_instance;
static void configure_console(void)
{
struct usart_config usart_conf;
usart_get_config_defaults(&usart_conf);
usart_conf.mux_setting = EDBG_CDC_SERCOM_MUX_SETTING;
usart_conf.pinmux_pad0 = EDBG_CDC_SERCOM_PINMUX_PAD0;
usart_conf.pinmux_pad1 = EDBG_CDC_SERCOM_PINMUX_PAD1;
usart_conf.pinmux_pad2 = EDBG_CDC_SERCOM_PINMUX_PAD2;
usart_conf.pinmux_pad3 = EDBG_CDC_SERCOM_PINMUX_PAD3;
usart_conf.baudrate = 115200;
stdio_serial_init(&usart_instance, EDBG_CDC_MODULE, &usart_conf);
usart_enable(&usart_instance);
}
Make Sure you call the configure_console after system_init() from the main function.
Now go to tools->extension manager. Add the terminal window extension.
Build and Run your program and open the terminal window from view-> terminal window. put the correct com port to which your device is running on and set the baud to 115200 and hit connect on the terminal window.
You should see the printf statements now. (Float doesn't get printed in Atmel studio)
I was recently puzzling over this myself. I has installed Atmel Studio 7.0 and was using the SAMD21 Dev Board via an example project in which a call to printf was made.
In the sample code I saw that there was a configuration section:
/*!
* \brief Initialize USART to communicate with on board EDBG - SERCOM
* with the following settings.
* - 8-bit asynchronous USART
* - No parity
* - One stop bit
* - 115200 baud
*/
static void configure_usart(void)
{
struct usart_config config_usart;
// Get the default USART configuration
usart_get_config_defaults(&config_usart);
// Configure the baudrate
config_usart.baudrate = 115200;
// Configure the pin multiplexing for USART
config_usart.mux_setting = EDBG_CDC_SERCOM_MUX_SETTING;
config_usart.pinmux_pad0 = EDBG_CDC_SERCOM_PINMUX_PAD0;
config_usart.pinmux_pad1 = EDBG_CDC_SERCOM_PINMUX_PAD1;
config_usart.pinmux_pad2 = EDBG_CDC_SERCOM_PINMUX_PAD2;
config_usart.pinmux_pad3 = EDBG_CDC_SERCOM_PINMUX_PAD3;
// route the printf output to the USART
stdio_serial_init(&usart_instance, EDBG_CDC_MODULE, &config_usart);
// enable USART
usart_enable(&usart_instance);
}
In windows device manager I saw that there was an "Atmel Corp. EDBG USB Port (COM3)" listed under "Ports". However, the one of the "Properties" of this port was listed as 9600 Bits per second. I changed this from 9600 to 115200 to be consistent with the config section above.
Finally, I ran PuTTY.exe and set the Connection-->Serial setting to COM3 and 115200 baud. Then I went to Session, then clicked the Serial Connection Type, then clicked the Open button. And, BAM, there's my printf output via PuTTY.