[dtrace-discuss] copyinstr() problem?

Manoj Joseph Manoj.Joseph at Sun.COM
Thu Aug 10 08:12:07 PDT 2006


Hi,

I am trying to dtrace a user mode application (devfsadm). And, I am 
running into a behaviour that I am unable to explain.

I print out a function argument by doing a copyinstr(). After the 
copyinstr(), the variable, apparently, 'automatically' gets initialized 
to zero.

This is the probe:
pid$target:devfsadm:minor_matches_rule:return
/self->node == "md" && arg1 && self->dcreate->device_class != 0/
{
	printf("%p ", self->dcreate->device_class);
	printf("[device class: %s] ", 
copyinstr((uintptr_t)(self->dcreate->device_class)));
	printf("%p ", self->dcreate->device_class);
}

The output is like this
  1  94444        minor_matches_rule:return feea0a04 [device class: 
pseudo] 0

self->dcreate->device_class is a valid address (feea0a04) before the 
copyinstr and zero right after it. How can this be?? Am I running into a 
bug? Am I missing something?

I tried assigning self->dcreate->device_class to another thread-local 
variable and doing the copyinstr() on it. I did not see the problem 
then. Hmmm...

I am attaching the entire script. It would be great if someone could 
take a look.

Regards,
Manoj
-------------- next part --------------
#! /usr/sbin/dtrace -CZs

/*
Run this script like this:
$ /workspace/mj153514/india/tests/switch/devfsadm.d \
    -I /workspace/mj153514/india/tests/switch/ \
    -c '/usr/sbin/devfsadm'  -32

*/

#include "devfsadm.h"

BEGIN
{
	self->create = (create_list_t *) NULL;
	self->dcreate = (devfsadm_create_t *)NULL;
}

pid$target::minor_process:entry
{
	self->t=1;
	self->noprint=0;
}

pid$target::devfsadm_print:entry
/self->t==1 && self->noprint == 0/
{
	self->noprint=1;
	self->node=copyinstr(arg2);
	self->minor=copyinstr(arg3);
}

pid$target::md_create:entry
{
	trace(probemod); trace(self->node);
}

pid$target:devfsadm:minor_matches_rule:entry
/self->node == "md"/
{
	self->create = (create_list_t *)copyin(arg2, sizeof(create_list_t));
	self->dcreate = (devfsadm_create_t *)copyin((uintptr_t)(self->create->create),
	    sizeof(devfsadm_create_t));
}

pid$target:devfsadm:minor_matches_rule:return
/self->node == "md" && arg1/
{

}

pid$target:devfsadm:minor_matches_rule:return
/self->node == "md" && arg1 && self->dcreate->device_class != 0/
{
	printf("%p ", self->dcreate->device_class);
	printf("[device class: %s] ", copyinstr((uintptr_t)(self->dcreate->device_class)));
	printf("%p ", self->dcreate->device_class);
}

pid$target:devfsadm:minor_matches_rule:return
/self->node == "md" && arg1 && self->dcreate->device_class == 0/
{
	printf("[device class: NULL]");
}

pid$target:devfsadm:minor_matches_rule:return
/self->node == "md" && arg1/
{
	printf("flags: %d type:%s drv_name %s \n",
	    self->dcreate->flags,
	    (self->dcreate->node_type ?
	    copyinstr((uintptr_t)self->dcreate->node_type) : 
	    "NULL"),
	    (self->dcreate->drv_name ?
	    copyinstr((uintptr_t)self->dcreate->drv_name) :
	    "NULL"));
}

pid$target:devfsadm:minor_matches_rule:return
{
	self->create = (create_list_t *) NULL;
	self->dcreate = (devfsadm_create_t *)NULL;
}

pid$target::minor_process:return
/self->node == "md"/
{
  printf("minor_process: %s-%s\n", self->node, self->minor);
}

pid$target::minor_process:return
{
  self->t=0;
  self->node = NULL;
  self->minor = NULL;
}


More information about the dtrace-discuss mailing list