Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
d4325152
Commit
d4325152
authored
Jul 30, 2005
by
Alexandre Julliard
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Added a separate device object to keep track of inodes that are on the
same device.
parent
386470be
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
93 additions
and
21 deletions
+93
-21
fd.c
server/fd.c
+93
-21
No files found.
server/fd.c
View file @
d4325152
...
@@ -165,14 +165,43 @@ static const struct object_ops fd_ops =
...
@@ -165,14 +165,43 @@ static const struct object_ops fd_ops =
fd_destroy
/* destroy */
fd_destroy
/* destroy */
};
};
/* device object */
#define DEVICE_HASH_SIZE 7
#define INODE_HASH_SIZE 17
struct
device
{
struct
object
obj
;
/* object header */
struct
list
entry
;
/* entry in device hash list */
dev_t
dev
;
/* device number */
struct
list
inode_hash
[
INODE_HASH_SIZE
];
/* inodes hash table */
};
static
void
device_dump
(
struct
object
*
obj
,
int
verbose
);
static
void
device_destroy
(
struct
object
*
obj
);
static
const
struct
object_ops
device_ops
=
{
sizeof
(
struct
device
),
/* size */
device_dump
,
/* dump */
no_add_queue
,
/* add_queue */
NULL
,
/* remove_queue */
NULL
,
/* signaled */
NULL
,
/* satisfied */
no_signal
,
/* signal */
no_get_fd
,
/* get_fd */
no_close_handle
,
/* close_handle */
device_destroy
/* destroy */
};
/* inode object */
/* inode object */
struct
inode
struct
inode
{
{
struct
object
obj
;
/* object header */
struct
object
obj
;
/* object header */
struct
list
entry
;
/* inode hash list entry */
struct
list
entry
;
/* inode hash list entry */
unsigned
int
hash
;
/* hashing code */
struct
device
*
device
;
/* device containing this inode */
dev_t
dev
;
/* device number */
ino_t
ino
;
/* inode number */
ino_t
ino
;
/* inode number */
struct
list
open
;
/* list of open file descriptors */
struct
list
open
;
/* list of open file descriptors */
struct
list
locks
;
/* list of file locks */
struct
list
locks
;
/* list of file locks */
...
@@ -544,11 +573,55 @@ void main_loop(void)
...
@@ -544,11 +573,55 @@ void main_loop(void)
/****************************************************************/
/****************************************************************/
/* inode functions */
/* device functions */
static
struct
list
device_hash
[
DEVICE_HASH_SIZE
];
/* retrieve the device object for a given fd, creating it if needed */
static
struct
device
*
get_device
(
dev_t
dev
)
{
struct
device
*
device
;
unsigned
int
i
,
hash
=
dev
%
DEVICE_HASH_SIZE
;
#define HASH_SIZE 37
if
(
device_hash
[
hash
].
next
)
{
LIST_FOR_EACH_ENTRY
(
device
,
&
device_hash
[
hash
],
struct
device
,
entry
)
if
(
device
->
dev
==
dev
)
return
(
struct
device
*
)
grab_object
(
device
);
}
else
list_init
(
&
device_hash
[
hash
]
);
/* not found, create it */
if
((
device
=
alloc_object
(
&
device_ops
)))
{
device
->
dev
=
dev
;
for
(
i
=
0
;
i
<
INODE_HASH_SIZE
;
i
++
)
list_init
(
&
device
->
inode_hash
[
i
]
);
list_add_head
(
&
device_hash
[
hash
],
&
device
->
entry
);
}
return
device
;
}
static
void
device_dump
(
struct
object
*
obj
,
int
verbose
)
{
struct
device
*
device
=
(
struct
device
*
)
obj
;
fprintf
(
stderr
,
"Device dev="
);
DUMP_LONG_LONG
(
device
->
dev
);
fprintf
(
stderr
,
"
\n
"
);
}
static
struct
list
inode_hash
[
HASH_SIZE
];
static
void
device_destroy
(
struct
object
*
obj
)
{
struct
device
*
device
=
(
struct
device
*
)
obj
;
unsigned
int
i
;
for
(
i
=
0
;
i
<
INODE_HASH_SIZE
;
i
++
)
assert
(
list_empty
(
&
device
->
inode_hash
[
i
])
);
list_remove
(
&
device
->
entry
);
/* remove it from the hash table */
}
/****************************************************************/
/* inode functions */
/* close all pending file descriptors in the closed list */
/* close all pending file descriptors in the closed list */
static
void
inode_close_pending
(
struct
inode
*
inode
)
static
void
inode_close_pending
(
struct
inode
*
inode
)
...
@@ -574,13 +647,10 @@ static void inode_close_pending( struct inode *inode )
...
@@ -574,13 +647,10 @@ static void inode_close_pending( struct inode *inode )
}
}
}
}
static
void
inode_dump
(
struct
object
*
obj
,
int
verbose
)
static
void
inode_dump
(
struct
object
*
obj
,
int
verbose
)
{
{
struct
inode
*
inode
=
(
struct
inode
*
)
obj
;
struct
inode
*
inode
=
(
struct
inode
*
)
obj
;
fprintf
(
stderr
,
"Inode dev="
);
fprintf
(
stderr
,
"Inode device=%p ino="
,
inode
->
device
);
DUMP_LONG_LONG
(
inode
->
dev
);
fprintf
(
stderr
,
" ino="
);
DUMP_LONG_LONG
(
inode
->
ino
);
DUMP_LONG_LONG
(
inode
->
ino
);
fprintf
(
stderr
,
"
\n
"
);
fprintf
(
stderr
,
"
\n
"
);
}
}
...
@@ -604,7 +674,7 @@ static void inode_destroy( struct object *obj )
...
@@ -604,7 +674,7 @@ static void inode_destroy( struct object *obj )
{
{
/* make sure it is still the same file */
/* make sure it is still the same file */
struct
stat
st
;
struct
stat
st
;
if
(
!
stat
(
fd
->
unlink
,
&
st
)
&&
st
.
st_dev
==
inode
->
dev
&&
st
.
st_ino
==
inode
->
ino
)
if
(
!
stat
(
fd
->
unlink
,
&
st
)
&&
st
.
st_dev
==
inode
->
dev
ice
->
dev
&&
st
.
st_ino
==
inode
->
ino
)
{
{
if
(
S_ISDIR
(
st
.
st_mode
))
rmdir
(
fd
->
unlink
);
if
(
S_ISDIR
(
st
.
st_mode
))
rmdir
(
fd
->
unlink
);
else
unlink
(
fd
->
unlink
);
else
unlink
(
fd
->
unlink
);
...
@@ -612,37 +682,39 @@ static void inode_destroy( struct object *obj )
...
@@ -612,37 +682,39 @@ static void inode_destroy( struct object *obj )
}
}
free
(
fd
);
free
(
fd
);
}
}
release_object
(
inode
->
device
);
}
}
/* retrieve the inode object for a given fd, creating it if needed */
/* retrieve the inode object for a given fd, creating it if needed */
static
struct
inode
*
get_inode
(
dev_t
dev
,
ino_t
ino
)
static
struct
inode
*
get_inode
(
dev_t
dev
,
ino_t
ino
)
{
{
struct
list
*
ptr
;
struct
device
*
device
;
struct
inode
*
inode
;
struct
inode
*
inode
;
unsigned
int
hash
=
(
dev
^
ino
)
%
HASH_SIZE
;
unsigned
int
hash
=
ino
%
INODE_
HASH_SIZE
;
if
(
inode_hash
[
hash
].
next
)
if
(
!
(
device
=
get_device
(
dev
)))
return
NULL
;
LIST_FOR_EACH_ENTRY
(
inode
,
&
device
->
inode_hash
[
hash
],
struct
inode
,
entry
)
{
{
LIST_FOR_EACH
(
ptr
,
&
inode_hash
[
hash
]
)
if
(
inode
->
ino
==
ino
)
{
{
inode
=
LIST_ENTRY
(
ptr
,
struct
inode
,
entry
);
release_object
(
device
);
if
(
inode
->
dev
==
dev
&&
inode
->
ino
==
ino
)
return
(
struct
inode
*
)
grab_object
(
inode
);
return
(
struct
inode
*
)
grab_object
(
inode
);
}
}
}
}
else
list_init
(
&
inode_hash
[
hash
]
);
/* not found, create it */
/* not found, create it */
if
((
inode
=
alloc_object
(
&
inode_ops
)))
if
((
inode
=
alloc_object
(
&
inode_ops
)))
{
{
inode
->
hash
=
hash
;
inode
->
device
=
device
;
inode
->
dev
=
dev
;
inode
->
ino
=
ino
;
inode
->
ino
=
ino
;
list_init
(
&
inode
->
open
);
list_init
(
&
inode
->
open
);
list_init
(
&
inode
->
locks
);
list_init
(
&
inode
->
locks
);
list_init
(
&
inode
->
closed
);
list_init
(
&
inode
->
closed
);
list_add_head
(
&
inode_hash
[
hash
],
&
inode
->
entry
);
list_add_head
(
&
device
->
inode_hash
[
hash
],
&
inode
->
entry
);
}
}
else
release_object
(
device
);
return
inode
;
return
inode
;
}
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment