From patchwork Tue Aug 9 12:01:05 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Torvald Riegel X-Patchwork-Id: 109201 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) by ozlabs.org (Postfix) with SMTP id F2065B6F70 for ; Tue, 9 Aug 2011 22:01:28 +1000 (EST) Received: (qmail 27810 invoked by alias); 9 Aug 2011 12:01:26 -0000 Received: (qmail 27797 invoked by uid 22791); 9 Aug 2011 12:01:25 -0000 X-SWARE-Spam-Status: No, hits=-6.9 required=5.0 tests=AWL, BAYES_00, RCVD_IN_DNSWL_HI, RP_MATCHES_RCVD, SPF_HELO_PASS, TW_RW X-Spam-Check-By: sourceware.org Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Tue, 09 Aug 2011 12:01:08 +0000 Received: from int-mx02.intmail.prod.int.phx2.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id p79C18TK023723 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Tue, 9 Aug 2011 08:01:08 -0400 Received: from [10.36.4.145] (vpn1-4-145.ams2.redhat.com [10.36.4.145]) by int-mx02.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id p79C16gw030416; Tue, 9 Aug 2011 08:01:07 -0400 Subject: Re: [trans-mem] Use per-transaction reader flags for the serial lock From: Torvald Riegel To: GCC Patches Cc: Richard Henderson , Aldy Hernandez In-Reply-To: <1312565593.3533.334.camel@triegel.csb> References: <1312565593.3533.334.camel@triegel.csb> Date: Tue, 09 Aug 2011 14:01:05 +0200 Message-ID: <1312891266.3533.368.camel@triegel.csb> Mime-Version: 1.0 X-IsSubscribed: yes Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org On Fri, 2011-08-05 at 19:33 +0200, Torvald Riegel wrote: > patch8: > > The first patch merely keeps a list of all threads with transactions, > registering and deregistering gtm_transaction objects during their > construction and destruction. The aligment attribute for the start of > the shared part of a gtm_transaction object relies on allocating those > objects on separate cachelines (and thus aligned at cacheline > granularity). This has not been implemented yet, but is requested by the > xmalloc call for gtm_transaction. Attached is a revised patch that puts HW_CACHELINE_SIZE into config/*/target.h instead of libitm_i.h. commit b76c73421c17ca9df7411129ca622f3143514f17 Author: Torvald Riegel Date: Fri Jul 29 22:12:14 2011 +0200 Maintain a list of all threads' transactions. * libitm_i.h (next_tx): Add list of all threads' transaction. * beginend.cc (GTM::gtm_transaction::begin_transaction): Register transaction with list of transactions and ... (thread_exit_handler): ... deregister here. * config/alpha/target.h: Add HW_CACHELINE_SIZE setting. * config/x86/target.h: Same. diff --git a/libitm/beginend.cc b/libitm/beginend.cc index 08592a3..fc7cb8d 100644 --- a/libitm/beginend.cc +++ b/libitm/beginend.cc @@ -29,6 +29,7 @@ using namespace GTM; __thread gtm_thread GTM::_gtm_thr; gtm_rwlock GTM::gtm_transaction::serial_lock; +gtm_transaction *GTM::gtm_transaction::list_of_tx = 0; gtm_stmlock GTM::gtm_stmlock_array[LOCK_ARRAY_SIZE]; gtm_version GTM::gtm_clock; @@ -75,6 +76,20 @@ thread_exit_handler(void *dummy __attribute__((unused))) { if (tx->nesting > 0) GTM_fatal("Thread exit while a transaction is still active."); + + // Deregister this transaction. + gtm_transaction::serial_lock.write_lock (); + gtm_transaction **prev = >m_transaction::list_of_tx; + for (; *prev; prev = &(*prev)->next_tx) + { + if (*prev == tx) + { + *prev = (*prev)->next_tx; + break; + } + } + gtm_transaction::serial_lock.write_unlock (); + delete tx; set_gtm_tx(NULL); } @@ -124,6 +139,12 @@ GTM::gtm_transaction::begin_transaction (uint32_t prop, const gtm_jmpbuf *jb) tx = new gtm_transaction; set_gtm_tx(tx); + // Register this transaction with the list of all threads' transactions. + serial_lock.write_lock (); + tx->next_tx = list_of_tx; + list_of_tx = tx; + serial_lock.write_unlock (); + if (pthread_once(&tx_release_once, thread_exit_init)) GTM_fatal("Initializing tx release TLS key failed."); // Any non-null value is sufficient to trigger releasing of this diff --git a/libitm/config/alpha/target.h b/libitm/config/alpha/target.h index 94ac59b..121546f 100644 --- a/libitm/config/alpha/target.h +++ b/libitm/config/alpha/target.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2009 Free Software Foundation, Inc. +/* Copyright (C) 2009, 2011 Free Software Foundation, Inc. Contributed by Richard Henderson . This file is part of the GNU Transactional Memory Library (libitm). @@ -36,6 +36,9 @@ typedef struct gtm_jmpbuf #define PAGE_SIZE 8192 #define FIXED_PAGE_SIZE 1 +/* The size of one line in hardware caches (in bytes). */ +#define HW_CACHELINE_SIZE 64 + static inline void cpu_relax (void) { diff --git a/libitm/config/x86/target.h b/libitm/config/x86/target.h index 758e773..197faeb 100644 --- a/libitm/config/x86/target.h +++ b/libitm/config/x86/target.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2008, 2009 Free Software Foundation, Inc. +/* Copyright (C) 2008, 2009, 2011 Free Software Foundation, Inc. Contributed by Richard Henderson . This file is part of the GNU Transactional Memory Library (libitm). @@ -56,6 +56,10 @@ typedef struct gtm_jmpbuf #define PAGE_SIZE 4096 #define FIXED_PAGE_SIZE 1 +/* The size of one line in hardware caches (in bytes). */ +#define HW_CACHELINE_SIZE 64 + + static inline void cpu_relax (void) { diff --git a/libitm/libitm_i.h b/libitm/libitm_i.h index 7d475be..f738ff7 100644 --- a/libitm/libitm_i.h +++ b/libitm/libitm_i.h @@ -187,11 +187,21 @@ struct gtm_transaction uint32_t restart_reason[NUM_RESTARTS]; uint32_t restart_total; + // *** The shared part of gtm_transaction starts here. *** + // Shared state is on separate cachelines to avoid false sharing with + // thread-local parts of gtm_transaction. + + // Points to the next transaction in the list of all threads' transactions. + gtm_transaction *next_tx __attribute__((__aligned__(HW_CACHELINE_SIZE))); + // The lock that provides access to serial mode. Non-serialized // transactions acquire read locks; a serialized transaction aquires // a write lock. static gtm_rwlock serial_lock; + // The head of the list of all threads' transactions. + static gtm_transaction *list_of_tx; + // In alloc.cc void commit_allocations (bool, aa_tree*); void record_allocation (void *, void (*)(void *));