summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authortorvald <torvald@138bc75d-0d04-0410-961f-82ee72b054a4>2011-06-30 17:12:13 +0000
committertorvald <torvald@138bc75d-0d04-0410-961f-82ee72b054a4>2011-06-30 17:12:13 +0000
commit53aaf755f28955aa98bc0720828a09776808f460 (patch)
treeb6e99417fd098ac9a3612e23c5f9b04e219583bb
parent6f3b93c949b76c3abb6fbd5c6333c43185fbbefd (diff)
downloadgcc-53aaf755f28955aa98bc0720828a09776808f460.tar.gz
Removed unnecessary trycommit, rollback, and registerThrownObject ABI functions.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/branches/transactional-memory@175716 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r--libitm/ChangeLog13
-rw-r--r--libitm/barrier.cc3
-rw-r--r--libitm/beginend.cc23
-rw-r--r--libitm/config/x86/x86_avx.cc2
-rw-r--r--libitm/config/x86/x86_sse.cc4
-rw-r--r--libitm/dispatch.h34
-rw-r--r--libitm/libitm.h7
-rw-r--r--libitm/libitm.map3
-rw-r--r--libitm/libitm.texi65
-rw-r--r--libitm/libitm_i.h4
-rw-r--r--libitm/method-serial.cc12
11 files changed, 97 insertions, 73 deletions
diff --git a/libitm/ChangeLog b/libitm/ChangeLog
index 7459fa2afbc..4d800007cbe 100644
--- a/libitm/ChangeLog
+++ b/libitm/ChangeLog
@@ -1,10 +1,21 @@
2011-06-30 Torvald Riegel <triegel@redhat.com>
+ * libitm_i.h (STATE_ABORTING): Remove.
+ * beginend.cc (_ITM_abortTransaction): Same.
+ (GTM::gtm_transaction::trycommit_and_finalize): Same.
+ * libitm.h (_ITM_registerThrownObject, _ITM_tryCommitTransaction): Remove.
+ (_ITM_rollbackTransaction): Remove.
+ * beginend.cc: Same.
+ * libitm.map: Same.
+ * libitm.texi: Document these ABI changes.
+
+2011-06-30 Torvald Riegel <triegel@redhat.com>
+
* libitm.texi: New file.
* Makefile.am: Add libitm.texi.
* Makefile.in: Rebuild.
-2011-05-25 Torvald Riegel <triegel@redhat.com>
+2011-06-30 Torvald Riegel <triegel@redhat.com>
* libitm_i.h: Move parts to common.h and dispatch.h.
* common.h: New file.
diff --git a/libitm/barrier.cc b/libitm/barrier.cc
index 10424d03fba..de84e04f7e9 100644
--- a/libitm/barrier.cc
+++ b/libitm/barrier.cc
@@ -40,6 +40,5 @@ bool abi_dispatch::memmove_overlap_check(void *dst, const void *src,
return true;
}
-CREATE_DISPATCH_FUNCTIONS(GTM::abi_disp()->_, )
-//CREATE_DISPATCH_FUNCTIONS(GTM::abi_dispatch::_, _static)
+CREATE_DISPATCH_FUNCTIONS(GTM::abi_disp()->, )
diff --git a/libitm/beginend.cc b/libitm/beginend.cc
index 7ed5073a662..9b16973b2a4 100644
--- a/libitm/beginend.cc
+++ b/libitm/beginend.cc
@@ -184,25 +184,12 @@ GTM::gtm_transaction::rollback ()
}
void ITM_REGPARM
-_ITM_rollbackTransaction (void)
-{
- gtm_transaction *tx = gtm_tx();
-
- assert ((tx->prop & pr_hasNoAbort) == 0);
- assert ((tx->state & gtm_transaction::STATE_ABORTING) == 0);
-
- tx->rollback ();
- tx->state |= gtm_transaction::STATE_ABORTING;
-}
-
-void ITM_REGPARM
_ITM_abortTransaction (_ITM_abortReason reason)
{
gtm_transaction *tx = gtm_tx();
assert (reason == userAbort);
assert ((tx->prop & pr_hasNoAbort) == 0);
- assert ((tx->state & gtm_transaction::STATE_ABORTING) == 0);
if (tx->state & gtm_transaction::STATE_IRREVOCABLE)
abort ();
@@ -238,7 +225,7 @@ GTM::gtm_transaction::trycommit ()
bool
GTM::gtm_transaction::trycommit_and_finalize ()
{
- if ((this->state & gtm_transaction::STATE_ABORTING) || trycommit ())
+ if (trycommit ())
{
abi_disp()->fini ();
set_gtm_tx (this->prev);
@@ -252,14 +239,6 @@ GTM::gtm_transaction::trycommit_and_finalize ()
return false;
}
-bool ITM_REGPARM
-_ITM_tryCommitTransaction (void)
-{
- gtm_transaction *tx = gtm_tx();
- assert ((tx->state & gtm_transaction::STATE_ABORTING) == 0);
- return tx->trycommit ();
-}
-
void ITM_NORETURN
GTM::gtm_transaction::restart (gtm_restart_reason r)
{
diff --git a/libitm/config/x86/x86_avx.cc b/libitm/config/x86/x86_avx.cc
index f81e3b8f59a..1f4ea538837 100644
--- a/libitm/config/x86/x86_avx.cc
+++ b/libitm/config/x86/x86_avx.cc
@@ -27,7 +27,7 @@
// ??? Use memcpy for now, until we have figured out how to best instantiate
// these loads/stores.
-CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M256, GTM::abi_disp()->_, )
+CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M256, GTM::abi_disp()->, )
void ITM_REGPARM
_ITM_LM256 (const _ITM_TYPE_M256 *ptr)
diff --git a/libitm/config/x86/x86_sse.cc b/libitm/config/x86/x86_sse.cc
index a8585e4759d..7440c949cb7 100644
--- a/libitm/config/x86/x86_sse.cc
+++ b/libitm/config/x86/x86_sse.cc
@@ -27,8 +27,8 @@
// ??? Use memcpy for now, until we have figured out how to best instantiate
// these loads/stores.
-CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M64, GTM::abi_disp()->_, )
-CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M128, GTM::abi_disp()->_, )
+CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M64, GTM::abi_disp()->, )
+CREATE_DISPATCH_FUNCTIONS_T_MEMCPY(M128, GTM::abi_disp()->, )
void ITM_REGPARM
_ITM_LM64 (const _ITM_TYPE_M64 *ptr)
diff --git a/libitm/dispatch.h b/libitm/dispatch.h
index 955cfabf0f6..3643503b5f7 100644
--- a/libitm/dispatch.h
+++ b/libitm/dispatch.h
@@ -32,24 +32,24 @@
// use M2 to create separate methods names for virtual and static)
// The _PV variants are for the pure-virtual methods in the base class.
#define ITM_READ_M(T, LSMOD, M, M2) \
- M _ITM_TYPE_##T ITM_REGPARM _ITM_##LSMOD##T##M2 (const _ITM_TYPE_##T *ptr)\
+ M _ITM_TYPE_##T ITM_REGPARM ITM_##LSMOD##T##M2 (const _ITM_TYPE_##T *ptr) \
{ \
return load(ptr, abi_dispatch::LSMOD); \
}
#define ITM_READ_M_PV(T, LSMOD, M, M2) \
- M _ITM_TYPE_##T ITM_REGPARM _ITM_##LSMOD##T##M2 (const _ITM_TYPE_##T *ptr)\
+ M _ITM_TYPE_##T ITM_REGPARM ITM_##LSMOD##T##M2 (const _ITM_TYPE_##T *ptr) \
= 0;
#define ITM_WRITE_M(T, LSMOD, M, M2) \
- M void ITM_REGPARM _ITM_##LSMOD##T##M2 (_ITM_TYPE_##T *ptr,\
+ M void ITM_REGPARM ITM_##LSMOD##T##M2 (_ITM_TYPE_##T *ptr, \
_ITM_TYPE_##T val) \
{ \
store(ptr, val, abi_dispatch::LSMOD); \
}
#define ITM_WRITE_M_PV(T, LSMOD, M, M2) \
- M void ITM_REGPARM _ITM_##LSMOD##T##M2 (_ITM_TYPE_##T *ptr,\
+ M void ITM_REGPARM ITM_##LSMOD##T##M2 (_ITM_TYPE_##T *ptr, \
_ITM_TYPE_##T val) \
= 0;
@@ -99,20 +99,20 @@
// Creates memcpy/memmove/memset methods.
#define CREATE_DISPATCH_METHODS_MEM() \
-virtual void _memtransfer(void *dst, const void* src, size_t size, \
+virtual void memtransfer(void *dst, const void* src, size_t size, \
bool may_overlap, ls_modifier dst_mod, ls_modifier src_mod) \
{ \
- _memtransfer_static(dst, src, size, may_overlap, dst_mod, src_mod); \
+ memtransfer_static(dst, src, size, may_overlap, dst_mod, src_mod); \
} \
-virtual void _memset(void *dst, int c, size_t size, ls_modifier mod) \
+virtual void memset(void *dst, int c, size_t size, ls_modifier mod) \
{ \
- _memset_static(dst, c, size, mod); \
+ memset_static(dst, c, size, mod); \
}
#define CREATE_DISPATCH_METHODS_MEM_PV() \
-virtual void _memtransfer(void *dst, const void* src, size_t size, \
+virtual void memtransfer(void *dst, const void* src, size_t size, \
bool may_overlap, ls_modifier dst_mod, ls_modifier src_mod) = 0; \
-virtual void _memset(void *dst, int c, size_t size, ls_modifier mod) = 0;
+virtual void memset(void *dst, int c, size_t size, ls_modifier mod) = 0;
// Creates ABI load/store functions that can target either a class or an
@@ -120,13 +120,13 @@ virtual void _memset(void *dst, int c, size_t size, ls_modifier mod) = 0;
#define ITM_READ(T, LSMOD, TARGET, M2) \
_ITM_TYPE_##T ITM_REGPARM _ITM_##LSMOD##T (const _ITM_TYPE_##T *ptr) \
{ \
- return TARGET##ITM_##LSMOD##T##M2(ptr); \
+ return TARGET ITM_##LSMOD##T##M2(ptr); \
}
#define ITM_WRITE(T, LSMOD, TARGET, M2) \
void ITM_REGPARM _ITM_##LSMOD##T (_ITM_TYPE_##T *ptr, _ITM_TYPE_##T val) \
{ \
- TARGET##ITM_##LSMOD##T##M2(ptr, val); \
+ TARGET ITM_##LSMOD##T##M2(ptr, val); \
}
// Creates ABI load/store functions for all load/store modifiers for a
@@ -144,12 +144,12 @@ virtual void _memset(void *dst, int c, size_t size, ls_modifier mod) = 0;
#define ITM_MEMTRANSFER_DEF(TARGET, M2, NAME, READ, WRITE) \
void ITM_REGPARM _ITM_memcpy##NAME(void *dst, const void *src, size_t size) \
{ \
- TARGET##memtransfer##M2 (dst, src, size, \
+ TARGET memtransfer##M2 (dst, src, size, \
false, GTM::abi_dispatch::WRITE, GTM::abi_dispatch::READ); \
} \
void ITM_REGPARM _ITM_memmove##NAME(void *dst, const void *src, size_t size) \
{ \
- TARGET##memtransfer##M2 (dst, src, size, \
+ TARGET memtransfer##M2 (dst, src, size, \
GTM::abi_dispatch::memmove_overlap_check(dst, src, size, \
GTM::abi_dispatch::WRITE, GTM::abi_dispatch::READ), \
GTM::abi_dispatch::WRITE, GTM::abi_dispatch::READ); \
@@ -158,7 +158,7 @@ void ITM_REGPARM _ITM_memmove##NAME(void *dst, const void *src, size_t size) \
#define ITM_MEMSET_DEF(TARGET, M2, WRITE) \
void ITM_REGPARM _ITM_memset##WRITE(void *dst, int c, size_t size) \
{ \
- TARGET##memset##M2 (dst, c, size, GTM::abi_dispatch::WRITE); \
+ TARGET memset##M2 (dst, c, size, GTM::abi_dispatch::WRITE); \
} \
@@ -210,7 +210,7 @@ void ITM_REGPARM _ITM_memset##WRITE(void *dst, int c, size_t size) \
_ITM_TYPE_##T ITM_REGPARM _ITM_##LSMOD##T (const _ITM_TYPE_##T *ptr)\
{ \
_ITM_TYPE_##T v; \
- TARGET##memtransfer##M2(&v, ptr, sizeof(_ITM_TYPE_##T), false, \
+ TARGET memtransfer##M2(&v, ptr, sizeof(_ITM_TYPE_##T), false, \
GTM::abi_dispatch::NONTXNAL, GTM::abi_dispatch::LSMOD); \
return v; \
}
@@ -218,7 +218,7 @@ void ITM_REGPARM _ITM_memset##WRITE(void *dst, int c, size_t size) \
#define ITM_WRITE_MEMCPY(T, LSMOD, TARGET, M2) \
void ITM_REGPARM _ITM_##LSMOD##T (_ITM_TYPE_##T *ptr, _ITM_TYPE_##T val)\
{ \
- TARGET##memtransfer##M2(ptr, &val, sizeof(_ITM_TYPE_##T), false, \
+ TARGET memtransfer##M2(ptr, &val, sizeof(_ITM_TYPE_##T), false, \
GTM::abi_dispatch::LSMOD, GTM::abi_dispatch::NONTXNAL); \
}
diff --git a/libitm/libitm.h b/libitm/libitm.h
index df89d33242f..abd4274e608 100644
--- a/libitm/libitm.h
+++ b/libitm/libitm.h
@@ -45,7 +45,7 @@ extern "C" {
#define ITM_NORETURN __attribute__((noreturn))
#define ITM_PURE __attribute__((transaction_pure))
-
+
/* The following are externally visible definitions and functions, though
only very few of these should be called by user code. */
@@ -91,6 +91,7 @@ typedef enum
pr_RaRBarriersOmitted = 0x0200,
pr_undoLogCode = 0x0400,
pr_preferUninstrumented = 0x0800,
+ /* Exception blocks are not used nor supported. */
pr_exceptionBlock = 0x1000,
pr_readOnly = 0x4000,
pr_hasElse = 0x200000,
@@ -138,12 +139,8 @@ extern _ITM_transactionId_t _ITM_getTransactionId(void) ITM_REGPARM;
extern uint32_t _ITM_beginTransaction(uint32_t, ...) ITM_REGPARM;
extern void _ITM_abortTransaction(_ITM_abortReason) ITM_REGPARM ITM_NORETURN;
-extern void _ITM_rollbackTransaction (void) ITM_REGPARM;
extern void _ITM_commitTransaction (void) ITM_REGPARM;
-extern bool _ITM_tryCommitTransaction(void) ITM_REGPARM;
-
-extern void _ITM_registerThrownObject (const void *, size_t) ITM_REGPARM;
extern void _ITM_changeTransactionMode (_ITM_transactionState) ITM_REGPARM;
diff --git a/libitm/libitm.map b/libitm/libitm.map
index 0d52a7c85d3..49d0b1b5ebb 100644
--- a/libitm/libitm.map
+++ b/libitm/libitm.map
@@ -12,9 +12,6 @@ LIBITM_1.0 {
_ITM_getTransactionId;
_ITM_inTransaction;
_ITM_libraryVersion;
- _ITM_registerThrownObject;
- _ITM_rollbackTransaction;
- _ITM_tryCommitTransaction;
_ITM_versionCompatible;
_ITM_registerTMCloneTable;
diff --git a/libitm/libitm.texi b/libitm/libitm.texi
index 8d8de8c174c..046b0bdd85d 100644
--- a/libitm/libitm.texi
+++ b/libitm/libitm.texi
@@ -221,25 +221,34 @@ reported for the dynamic scope as well, not just for the lexical scope
(@code{hasNoAbort}). Without this, a library cannot exploit this together
with flat nesting.
-@strong{TODO} @code{exceptionBlock?}
+@code{exceptionBlock} is not supported because exception blocks are not used.
@subsubsection [No changes] Windows exception state
@subsubsection [No changes] Other machine state
-@subsubsection Results from beginTransaction
-@strong{TODO} @code{abortTransaction} supported?
+@subsubsection [No changes] Results from beginTransaction
@subsection Aborting a transaction
-@strong{TODO} make consistent with EH.
-@subsection Committing a transaction
-@strong{TODO} make consistent with EH.
+@code{_ITM_rollbackTransaction} is not supported. @code{_ITM_abortTransaction}
+is supported but the abort reason @code{exceptionBlockAbort} is not (and there
+are no exception blocks in general, so the related cases also do not have to
+be considered).
-@subsection Exception handling support
+@subsection Committing a transaction
-@strong{TODO} Document wrappers. Document code generated for commit, perhaps
-with examples similar to those in the specification. What can be removed from
-the ABI in turn? Document requirements on libstdc++ (@code{_cxa_tm_cleanup()}).
+The exception handling (EH) scheme is different. The Intel ABI requires the
+@code{_ITM_tryCommitTransaction} function that will return even when the
+commit failed and will have to be matched with calls to either
+@code{_ITM_abortTransaction} or @code{_ITM_commitTransaction}. In contrast,
+gcc relies on transactional wrappers for the functions of the Exception
+Handling ABI and on one additional commit function (shown below). This allows
+the TM to keep track of EH internally and thus it does not have to embed the
+cleanup of EH state into the existing EH code in the program.
+@code{_ITM_tryCommitTransaction} is not supported.
+@code{_ITM_commitTransactionToId} is also not supported because the
+propagation of thrown exceptions will not bypass commits of nested
+transactions.
@example
void _ITM_commitTransactionEH(void *exc_ptr) ITM_REGPARM;
@@ -249,6 +258,42 @@ void *_ITM_cxa_begin_catch (void *exc_ptr);
void _ITM_cxa_end_catch (void);
@end example
+@code{_ITM_commitTransactionEH} must be called to commit a transaction if an
+exception could be in flight at this position in the code. @code{exc_ptr} is
+the current exception or zero if there is no current exception.
+The @code{_ITM_cxa...} functions are transactional wrappers for the respective
+@code{__cxa...} functions and must be called instead of these in transactional
+code.
+
+To support this EH scheme, libstdc++ needs to provide one additional function
+(@code{_cxa_tm_cleanup}), which is used by the TM to clean up the exception
+handling state while rolling back a transaction:
+
+@example
+void __cxa_tm_cleanup (void *unthrown_obj, void *cleanup_exc,
+ unsigned int caught_count);
+@end example
+
+@code{unthrown_obj} is non-null if the program called
+@code{__cxa_allocate_exception} for this exception but did not yet called
+@code{__cxa_throw} for it. @code{cleanup_exc} is non-null if the program is
+currently processing a cleanup along an exception path but has not caught this
+exception yet. @code{caught_count} is the nesting depth of
+@code{__cxa_begin_catch} within the transaction (which can be counted by the TM
+using @code{_ITM_cxa_begin_catch} and @code{_ITM_cxa_end_catch});
+@code{__cxa_tm_cleanup} then performs rollback by essentially performing
+@code{__cxa_end_catch} that many times.
+
+
+
+@subsection Exception handling support
+
+Currently, there is no support for functionality like
+@code{__transaction_cancel throw} as described in the C++ TM specification.
+Supporting this should be possible with the EH scheme explained previously
+because via the transactional wrappers for the EH ABI, the TM is able to
+observe and intercept EH.
+
@subsection [No changes] Transition to serial--irrevocable mode
@subsection [No changes] Data transfer functions
diff --git a/libitm/libitm_i.h b/libitm/libitm_i.h
index d323d45a382..98c2c753b06 100644
--- a/libitm/libitm_i.h
+++ b/libitm/libitm_i.h
@@ -146,10 +146,6 @@ struct gtm_transaction
// Set if the serial-irrevocable dispatch table is installed.
// Implies that no logging is being done, and abort is not possible.
static const uint32_t STATE_IRREVOCABLE = 0x0002;
- // Set if we're in the process of aborting the transaction. This is
- // used when _ITM_rollbackTransaction is called to begin the abort
- // and ends with _ITM_commitTransaction.
- static const uint32_t STATE_ABORTING = 0x0004;
// A bitmask of the above.
uint32_t state;
diff --git a/libitm/method-serial.cc b/libitm/method-serial.cc
index 71208ec5dac..a6fbc7f6b5b 100644
--- a/libitm/method-serial.cc
+++ b/libitm/method-serial.cc
@@ -55,7 +55,8 @@ class serial_dispatch : public abi_dispatch
*addr = value;
}
- static void _memtransfer_static(void *dst, const void* src, size_t size,
+ public:
+ static void memtransfer_static(void *dst, const void* src, size_t size,
bool may_overlap, ls_modifier dst_mod, ls_modifier src_mod)
{
if (!may_overlap)
@@ -64,7 +65,7 @@ class serial_dispatch : public abi_dispatch
::memmove(dst, src, size);
}
- static void _memset_static(void *dst, int c, size_t size, ls_modifier mod)
+ static void memset_static(void *dst, int c, size_t size, ls_modifier mod)
{
::memset(dst, c, size);
}
@@ -72,7 +73,6 @@ class serial_dispatch : public abi_dispatch
CREATE_DISPATCH_METHODS(virtual, )
CREATE_DISPATCH_METHODS_MEM()
- public:
virtual bool trycommit() { return true; }
virtual void rollback() { abort(); }
virtual void reinit() { }
@@ -107,16 +107,16 @@ public:
if (dst_mod != WaW && dst_mod != NONTXNAL)
log(dst, size);
if (!may_overlap)
- memcpy(dst, src, size);
+ ::memcpy(dst, src, size);
else
- memmove(dst, src, size);
+ ::memmove(dst, src, size);
}
static void memset_static(void *dst, int c, size_t size, ls_modifier mod)
{
if (mod != WaW)
log(dst, size);
- memset(dst, c, size);
+ ::memset(dst, c, size);
}
// Local undo will handle this.