Skip to content

Commit

Permalink
client: don't allocate some commit batches
Browse files Browse the repository at this point in the history
When commiting, the client.Txn used to allocate a slice of requests
(inside a BatchRequest), a RequestUnion, and an EndTransactionRequest.
This shows up on profiles of a single node read-heavy workload.
This patch moves to pre-allocating these inside a Txn. This works since
there's no concurrent commits on a single txn.

Release note: None
  • Loading branch information
andreimatei committed Sep 26, 2018
1 parent 1f95897 commit 06c1adf
Showing 1 changed file with 34 additions and 2 deletions.
36 changes: 34 additions & 2 deletions pkg/internal/client/txn.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,18 @@ type Txn struct {
// typ indicates the type of transaction.
typ TxnType

// alloc holds pre-allocated fields that can be used to avoid heap allocations
// for batches with lifetimes tied to a Txn.
// TODO(andrei): A lot more things should be pre-allocated or otherwise pooled
// - in particular the roachpb.Transaction proto and the TxnCoordSender which
// are quite large. Pooling them would also force us to clean up their
// lifetimes, which is a good idea on its own.
alloc struct {
requests [1]roachpb.RequestUnion
etUnion roachpb.RequestUnion_EndTransaction
et roachpb.EndTransactionRequest
}

// gatewayNodeID, if != 0, is the ID of the node on whose behalf this
// transaction is running. Normally this is the current node, but in the case
// of Txns created on remote nodes by DistSQL this will be the gateway.
Expand Down Expand Up @@ -509,8 +521,7 @@ func (txn *Txn) Run(ctx context.Context, b *Batch) error {
}

func (txn *Txn) commit(ctx context.Context) error {
var ba roachpb.BatchRequest
ba.Add(endTxnReq(true /* commit */, txn.deadline(), txn.systemConfigTrigger))
ba := txn.getCommitReq(txn.deadline(), txn.systemConfigTrigger)
_, pErr := txn.Send(ctx, ba)
if pErr == nil {
for _, t := range txn.commitTriggers {
Expand All @@ -534,6 +545,27 @@ func (txn *Txn) CleanupOnError(ctx context.Context, err error) {
}
}

func (txn *Txn) getCommitReq(deadline *hlc.Timestamp, hasTrigger bool) roachpb.BatchRequest {
ba := roachpb.BatchRequest{
Requests: txn.alloc.requests[:1],
}
etReq := &txn.alloc.et
etUnion := &txn.alloc.etUnion
ba.Requests[0].Value = etUnion
etUnion.EndTransaction = etReq
etReq.Reset()
etReq.Commit = true
etReq.Deadline = deadline
if hasTrigger {
etReq.InternalCommitTrigger = &roachpb.InternalCommitTrigger{
ModifiedSpanTrigger: &roachpb.ModifiedSpanTrigger{
SystemConfigSpan: true,
},
}
}
return ba
}

// Commit is the same as CommitOrCleanup but will not attempt to clean
// up on failure. This can be used when the caller is prepared to do proper
// cleanup.
Expand Down

0 comments on commit 06c1adf

Please sign in to comment.