Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 27 Aug 2002 20:10:14 -0700
From:      Terry Lambert <tlambert2@mindspring.com>
To:        Pawel Jakub Dawidek <nick@garage.freebsd.pl>
Cc:        freebsd-hackers@freebsd.org
Subject:   Re: Replacing kernel functions.
Message-ID:  <3D6C3F16.EC09BDB@mindspring.com>
References:  <20020828021016.GB31943@garage.freebsd.pl>

next in thread | previous in thread | raw e-mail | index | archive | help
Pawel Jakub Dawidek wrote:
> But there is no way to do what I want to do.
> I need to write something that give me filename of open file
> when I gave an descriptor.
> So I cache all open() calls. But there is a problem how to clean up
> on close. When descriptors are closed by syscalls (close(), sys_exit())
> there is no problem to catch it, by what when process will be killed
> by signal from kernel?
> So I'm replacing ffree() function from /sys/kern/kern_descrip.c in my
> evil way:)
> 
> I know that this way is fucked up, but I have no idea how to made
> this in diffrent (nice) way.


The easiest way to do this is to take nullfs and modify it so
that it caches the name of the file for the vnode that is
returned as a value pointed to by the per layer vnode data
area, e.g. modify struct null_node to add a null_name pointer:

struct null_node {
        struct lock             null_lock;      /* Lock for this vnode. MBF */
        struct lock             *null_vnlock;   /* lock of lower vnode in the st
ack */
        LIST_ENTRY(null_node)   null_hash;      /* Hash list */
        struct vnode            *null_lowervp;  /* VREFed once */
        struct vnode            *null_vnode;    /* Back pointer */
	char			*null_name;	/* Name used to open */
};

Then add an vop_ioctl() command entry that can retrieve the name
out of the null_name entry, and cache the value on the way out
of any null_lookup(), if it's not already non-NULL.

Then in null_reclaim(), before freeing vdata, cast it to a
(struct null_node *), and free vdata->null_name.

This method requires you to stack a layer, which need an explicit
mount and has some additiona overhead from converting the page
get/put to use read/write operations, but it will do what you want,
if all you want is the node name.

The downside of the requirement of the explicit mount is that
you tie the semantics you want to an externally visible operation,
so you can't hide the fact that you did this from users, but then
you couldn't hide the fact that you mounted an FFS instead of a
CD9660 from users, if the semantic you wanted was writeability,
or support for chflags.  8-).


Since directories are not allowed to have multiple hard links,
you can do a traversal to root using the parent vnode pointer,
which is passed in as part of the lookup context, in order to
get the intermediate path components (basically, if you cache
the full path this way, you will get the path minus that file
name itself from the parent's cached path, automatically).

By default, ioctl() is not supported (trapped) by the nullfs
layer, so you will need to add a descriptor and a function
implementation, but that's pretty trivial.

Stacking in FreeBSD is really ugly compared to what it could
be (IMO), but it's workable.



> +> Personally, I've used this technique myself, for the purposes
> +> of code instrumentation for profiling on an OD for which I
> +> lacked source code, but I would *never* consider exporting
> +> this as a general API.
> 
> So when all kernel functions addresses will be in some tab just like
> syscalls addresses?:)

The symbol table of the object file; in this case, the kernel.

-- Terry

To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-hackers" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?3D6C3F16.EC09BDB>