Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
cython
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Labels
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Commits
Open sidebar
nexedi
cython
Commits
40cb5671
Commit
40cb5671
authored
Feb 04, 2015
by
Robert Bradshaw
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Avoid incorrect copy when reference is stored to a temporary variable.
parent
52b8a0e8
Changes
4
Show whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
45 additions
and
5 deletions
+45
-5
Cython/Compiler/ExprNodes.py
Cython/Compiler/ExprNodes.py
+3
-2
Cython/Compiler/PyrexTypes.py
Cython/Compiler/PyrexTypes.py
+18
-1
Cython/Utility/ModuleSetupCode.c
Cython/Utility/ModuleSetupCode.c
+13
-1
tests/run/cpp_template_ref_args.pyx
tests/run/cpp_template_ref_args.pyx
+11
-1
No files found.
Cython/Compiler/ExprNodes.py
View file @
40cb5671
...
...
@@ -4739,8 +4739,7 @@ class SimpleCallNode(CallNode):
# func_type.exception_check = True
if
self
.
is_temp
and
self
.
type
.
is_reference
:
# TODO: Avoid the copy.
self
.
type
=
self
.
type
.
ref_base_type
self
.
type
=
PyrexTypes
.
CFakeReferenceType
(
self
.
type
.
ref_base_type
)
# Called in 'nogil' context?
self
.
nogil
=
env
.
nogil
...
...
@@ -5702,6 +5701,8 @@ class AttributeNode(ExprNode):
self
.
op
=
"->"
elif
obj_type
.
is_extension_type
or
obj_type
.
is_builtin_type
:
self
.
op
=
"->"
elif
obj_type
.
is_reference
and
obj_type
.
is_fake_reference
:
self
.
op
=
"->"
else
:
self
.
op
=
"."
if
obj_type
.
has_attributes
:
...
...
Cython/Compiler/PyrexTypes.py
View file @
40cb5671
...
...
@@ -2422,6 +2422,7 @@ class CNullPtrType(CPtrType):
class
CReferenceType
(
BaseType
):
is_reference
=
1
is_fake_reference
=
0
def
__init__
(
self
,
base_type
):
self
.
ref_base_type
=
base_type
...
...
@@ -2444,7 +2445,7 @@ class CReferenceType(BaseType):
if
base_type
==
self
.
ref_base_type
:
return
self
else
:
return
CReferenceType
(
base_type
)
return
type
(
self
)
(
base_type
)
def
deduce_template_params
(
self
,
actual
):
return
self
.
ref_base_type
.
deduce_template_params
(
actual
)
...
...
@@ -2453,6 +2454,22 @@ class CReferenceType(BaseType):
return
getattr
(
self
.
ref_base_type
,
name
)
class
CFakeReferenceType
(
CReferenceType
):
is_fake_reference
=
1
def
__repr__
(
self
):
return
"<CFakeReferenceType %s>"
%
repr
(
self
.
ref_base_type
)
def
__str__
(
self
):
return
"%s [&]"
%
self
.
ref_base_type
def
declaration_code
(
self
,
entity_code
,
for_display
=
0
,
dll_linkage
=
None
,
pyrex
=
0
):
#print "CReferenceType.declaration_code: pointer to", self.base_type ###
return
"__Pyx_FakeReference<%s> %s"
%
(
self
.
ref_base_type
.
empty_declaration_code
(),
entity_code
)
class
CFuncType
(
CType
):
# return_type CType
# args [CFuncTypeArg]
...
...
Cython/Utility/ModuleSetupCode.c
View file @
40cb5671
...
...
@@ -217,12 +217,24 @@ static CYTHON_INLINE float __PYX_NAN() {
#define __Pyx_void_to_None(void_result) (void_result, Py_INCREF(Py_None), Py_None)
// Work around clang bug http://stackoverflow.com/questions/21847816/c-invoke-nested-template-class-destructor
#ifdef __cplusplus
// Work around clang bug http://stackoverflow.com/questions/21847816/c-invoke-nested-template-class-destructor
template
<
typename
T
>
void
__Pyx_call_destructor
(
T
*
x
)
{
x
->~
T
();
}
// Used for temporary variables of "reference" type.
template
<
typename
T
>
class
__Pyx_FakeReference
{
public:
__Pyx_FakeReference
()
:
ptr
(
NULL
)
{
}
__Pyx_FakeReference
(
T
&
ref
)
:
ptr
(
&
ref
)
{
}
T
*
operator
->
()
{
return
ptr
;
}
operator
T
&
()
{
return
*
ptr
;
}
private:
T
*
ptr
;
};
#endif
/////////////// UtilityFunctionPredeclarations.proto ///////////////
...
...
tests/run/cpp_template_ref_args.pyx
View file @
40cb5671
...
...
@@ -5,8 +5,9 @@ cdef extern from "cpp_template_ref_args.h":
cdef
cppclass
Bar
[
T
]:
Bar
()
Bar
[
T
]
&
ref
()
# bug: Bar[T] created before class fully defined
T
value
Bar
[
T
]
&
ref
()
except
+
cdef
cppclass
Foo
[
T
]:
Foo
()
...
...
@@ -28,3 +29,12 @@ def test_template_ref_arg(int x):
bar
.
value
=
x
return
foo
.
bar_value
(
bar
.
ref
())
def
test_template_ref_attr
(
int
x
):
"""
>>> test_template_ref_attr(4)
4
"""
cdef
Bar
[
int
]
bar
bar
.
value
=
x
return
bar
.
ref
().
value
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