Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
R
riscv-gcc-1
Overview
Overview
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
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
lvzhengyang
riscv-gcc-1
Commits
c19f8e35
Commit
c19f8e35
authored
Jul 10, 2003
by
Nicola Pero
Committed by
Nicola Pero
Jul 10, 2003
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Fixed rare threading problem
From-SVN: r69181
parent
633221db
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
67 additions
and
14 deletions
+67
-14
libobjc/ChangeLog
+9
-0
libobjc/sendmsg.c
+58
-14
No files found.
libobjc/ChangeLog
View file @
c19f8e35
Thu Jul 10 10:27:43 2003 Nicola Pero <n.pero@mi.flashnet.it>
libobjc/9969
* sendmsg.c (get_imp): Fixed rare threading problem.
(__objc_responds_to): Similar fixes.
(objc_msg_lookup): Similar fixes.
(__objc_init_install_dtable): Lock the runtime before checking if the
table is installed.
2003-05-23 Nathanael Nerode <neroden@gcc.gnu.org>
* hash.c, init.c, libobjc.def, libobjc_entry.c, linking.m,
...
...
libobjc/sendmsg.c
View file @
c19f8e35
...
...
@@ -119,6 +119,14 @@ __inline__
IMP
get_imp
(
Class
class
,
SEL
sel
)
{
/* In a vanilla implementation we would first check if the dispatch
table is installed. Here instead, to get more speed in the
standard case (that the dispatch table is installed) we first try
to get the imp using brute force. Only if that fails, we do what
we should have been doing from the very beginning, that is, check
if the dispatch table needs to be installed, install it if it's
not installed, and retrieve the imp from the table if it's
installed. */
void
*
res
=
sarray_get_safe
(
class
->
dtable
,
(
size_t
)
sel
->
sel_id
);
if
(
res
==
0
)
{
...
...
@@ -127,7 +135,16 @@ get_imp (Class class, SEL sel)
{
/* The dispatch table needs to be installed. */
objc_mutex_lock
(
__objc_runtime_mutex
);
__objc_install_dispatch_table_for_class
(
class
);
/* Double-checked locking pattern: Check
__objc_uninstalled_dtable again in case another thread
installed the dtable while we were waiting for the lock
to be released. */
if
(
class
->
dtable
==
__objc_uninstalled_dtable
)
{
__objc_install_dispatch_table_for_class
(
class
);
}
objc_mutex_unlock
(
__objc_runtime_mutex
);
/* Call ourselves with the installed dispatch table
and get the real method */
...
...
@@ -135,10 +152,22 @@ get_imp (Class class, SEL sel)
}
else
{
/* The dispatch table has been installed so the
method just doesn't exist for the class.
Return the forwarding implementation. */
res
=
__objc_get_forward_imp
(
sel
);
/* The dispatch table has been installed. */
/* Get the method from the dispatch table (we try to get it
again in case another thread has installed the dtable just
after we invoked sarray_get_safe, but before we checked
class->dtable == __objc_uninstalled_dtable).
*/
res
=
sarray_get_safe
(
class
->
dtable
,
(
size_t
)
sel
->
sel_id
);
if
(
res
==
0
)
{
/* The dispatch table has been installed, and the method
is not in the dispatch table. So the method just
doesn't exist for the class. Return the forwarding
implementation. */
res
=
__objc_get_forward_imp
(
sel
);
}
}
}
return
res
;
...
...
@@ -157,7 +186,10 @@ __objc_responds_to (id object, SEL sel)
if
(
object
->
class_pointer
->
dtable
==
__objc_uninstalled_dtable
)
{
objc_mutex_lock
(
__objc_runtime_mutex
);
__objc_install_dispatch_table_for_class
(
object
->
class_pointer
);
if
(
object
->
class_pointer
->
dtable
==
__objc_uninstalled_dtable
)
{
__objc_install_dispatch_table_for_class
(
object
->
class_pointer
);
}
objc_mutex_unlock
(
__objc_runtime_mutex
);
}
...
...
@@ -192,10 +224,19 @@ objc_msg_lookup (id receiver, SEL op)
}
else
{
/* The dispatch table has been installed so the
method just doesn't exist for the class.
Attempt to forward the method. */
result
=
__objc_get_forward_imp
(
op
);
/* The dispatch table has been installed. Check again
if the method exists (just in case the dispatch table
has been installed by another thread after we did the
previous check that the method exists).
*/
result
=
sarray_get_safe
(
receiver
->
class_pointer
->
dtable
,
(
sidx
)
op
->
sel_id
);
if
(
result
==
0
)
{
/* If the method still just doesn't exist for the
class, attempt to forward the method. */
result
=
__objc_get_forward_imp
(
op
);
}
}
}
return
result
;
...
...
@@ -239,13 +280,16 @@ __objc_init_dispatch_tables ()
static
void
__objc_init_install_dtable
(
id
receiver
,
SEL
op
__attribute__
((
__unused__
)))
{
objc_mutex_lock
(
__objc_runtime_mutex
);
/* This may happen, if the programmer has taken the address of a
method before the dtable was initialized... too bad for him! */
if
(
receiver
->
class_pointer
->
dtable
!=
__objc_uninstalled_dtable
)
return
;
objc_mutex_lock
(
__objc_runtime_mutex
);
{
objc_mutex_unlock
(
__objc_runtime_mutex
);
return
;
}
if
(
CLS_ISCLASS
(
receiver
->
class_pointer
))
{
/* receiver is an ordinary object */
...
...
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