Skip to content

Commit c4283dd

Browse files
committed
C++: Support __is_assignable builtin
While here fix the documentation of `__is_trivially_assignable` and `__is_nothrow_assignable`.
1 parent 9876c39 commit c4283dd

File tree

4 files changed

+36
-9
lines changed

4 files changed

+36
-9
lines changed

cpp/ql/lib/semmle/code/cpp/exprs/BuiltInOperations.qll

Lines changed: 21 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -612,13 +612,10 @@ class BuiltInOperationIsTriviallyDestructible extends BuiltInOperation, @istrivi
612612
* The `__is_trivially_assignable` built-in operation (used by some
613613
* implementations of the `<type_traits>` header).
614614
*
615-
* Returns `true` if the assignment operator `C::operator =(const C& c)` is
616-
* trivial.
615+
* Returns `true` if the assignment operator `C::operator =(const D& d)` is
616+
* trivial (i.e., it will not call any operation that is non-trivial).
617617
* ```
618-
* template<typename T>
619-
* struct is_trivially_assignable
620-
* : public integral_constant<bool, __is_trivially_assignable(T) >
621-
* { };
618+
* bool v = __is_trivially_assignable(MyType1, MyType2);
622619
* ```
623620
*/
624621
class BuiltInOperationIsTriviallyAssignable extends BuiltInOperation, @istriviallyassignableexpr {
@@ -631,10 +628,10 @@ class BuiltInOperationIsTriviallyAssignable extends BuiltInOperation, @istrivial
631628
* The `__is_nothrow_assignable` built-in operation (used by some
632629
* implementations of the `<type_traits>` header).
633630
*
634-
* Returns true if there exists a `C::operator =(const C& c) nothrow`
631+
* Returns true if there exists a `C::operator =(const D& d) nothrow`
635632
* assignment operator (i.e, with an empty exception specification).
636633
* ```
637-
* bool v = __is_nothrow_assignable(MyType);
634+
* bool v = __is_nothrow_assignable(MyType1, MyType2);
638635
* ```
639636
*/
640637
class BuiltInOperationIsNothrowAssignable extends BuiltInOperation, @isnothrowassignableexpr {
@@ -643,6 +640,22 @@ class BuiltInOperationIsNothrowAssignable extends BuiltInOperation, @isnothrowas
643640
override string getAPrimaryQlClass() { result = "BuiltInOperationIsNothrowAssignable" }
644641
}
645642

643+
/**
644+
* The `__is_assignable` built-in operation (used by some implementations
645+
* of the `<type_traits>` header).
646+
*
647+
* Returns true if there exists a `C::operator =(const D& d)` assignment
648+
* operator.
649+
* ```
650+
* bool v = __is_assignable(MyType1, MyType2);
651+
* ```
652+
*/
653+
class BuiltInOperationIsAssignable extends BuiltInOperation, @isassignable {
654+
override string toString() { result = "__is_assignable" }
655+
656+
override string getAPrimaryQlClass() { result = "BuiltInOperationIsAssignable" }
657+
}
658+
646659
/**
647660
* The `__is_standard_layout` built-in operation (used by some implementations
648661
* of the `<type_traits>` header).

cpp/ql/lib/semmlecode.cpp.dbscheme

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1650,6 +1650,7 @@ case @expr.kind of
16501650
| 327 = @co_await
16511651
| 328 = @co_yield
16521652
| 329 = @temp_init
1653+
| 330 = @isassignable
16531654
;
16541655

16551656
@var_args_expr = @vastartexpr
@@ -1711,6 +1712,7 @@ case @expr.kind of
17111712
| @isfinalexpr
17121713
| @builtinchooseexpr
17131714
| @builtincomplex
1715+
| @isassignable
17141716
;
17151717

17161718
new_allocated_type(

cpp/ql/test/library-tests/builtins/type_traits/expr.expected

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -296,3 +296,12 @@
296296
| ms.cpp:255:24:255:43 | a_struct | | <none> |
297297
| ms.cpp:256:24:256:49 | __is_final | a_final_struct | 1 |
298298
| ms.cpp:256:24:256:49 | a_final_struct | | <none> |
299+
| ms.cpp:258:29:258:62 | __is_assignable | a_struct,a_struct | 1 |
300+
| ms.cpp:258:29:258:62 | a_struct | | <none> |
301+
| ms.cpp:258:29:258:62 | a_struct | | <none> |
302+
| ms.cpp:259:29:259:59 | __is_assignable | a_struct,empty | 0 |
303+
| ms.cpp:259:29:259:59 | a_struct | | <none> |
304+
| ms.cpp:259:29:259:59 | empty | | <none> |
305+
| ms.cpp:260:29:260:57 | __is_assignable | a_struct,int | 0 |
306+
| ms.cpp:260:29:260:57 | a_struct | | <none> |
307+
| ms.cpp:260:29:260:57 | int | | <none> |

cpp/ql/test/library-tests/builtins/type_traits/ms.cpp

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -254,5 +254,8 @@ void f(void) {
254254

255255
bool b_is_final1 = __is_final(a_struct);
256256
bool b_is_final2 = __is_final(a_final_struct);
257-
}
258257

258+
bool b_is_assignable1 = __is_assignable(a_struct,a_struct);
259+
bool b_is_assignable2 = __is_assignable(a_struct,empty);
260+
bool b_is_assignable3 = __is_assignable(a_struct,int);
261+
}

0 commit comments

Comments
 (0)