Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code | Sign in
(399)

Delta Between Two Patch Sets: src/pkg/exp/sql/fakedb_test.go

Issue 5533077: code review 5533077: sql: fix potential corruption in QueryRow.Scan into a *... (Closed)
Left Patch Set: diff -r c6318b5115e5 https://go.googlecode.com/hg/ Created 12 years, 2 months ago
Right Patch Set: diff -r 29382b5af719 https://go.googlecode.com/hg/ Created 12 years, 2 months ago
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments. Please Sign in to add in-line comments.
Jump to:
Left: Side by side diff | Download
Right: Side by side diff | Download
« no previous file with change/comment | « no previous file | src/pkg/exp/sql/sql.go » ('j') | no next file with change/comment »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
LEFTRIGHT
1 // Copyright 2011 The Go Authors. All rights reserved. 1 // Copyright 2011 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style 2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file. 3 // license that can be found in the LICENSE file.
4 4
5 package sql 5 package sql
6 6
7 import ( 7 import (
8 "errors" 8 "errors"
9 "fmt" 9 "fmt"
10 "io" 10 "io"
(...skipping 495 matching lines...) Expand 10 before | Expand all | Expand 10 after
506 tx.c.currTx = nil 506 tx.c.currTx = nil
507 return nil 507 return nil
508 } 508 }
509 509
510 type rowsCursor struct { 510 type rowsCursor struct {
511 cols []string 511 cols []string
512 pos int 512 pos int
513 rows []*row 513 rows []*row
514 closed bool 514 closed bool
515 515
516 » // a clone of slices to give out to clients, indexes by the 516 » // a clone of slices to give out to clients, indexed by the
517 // the original slice's first byte address. we clone them 517 // the original slice's first byte address. we clone them
518 // just so we're able to corrupt them on close. 518 // just so we're able to corrupt them on close.
519 bytesClone map[*byte][]byte 519 bytesClone map[*byte][]byte
520
521 // set of bytes to intentionally corrupt on close, simulating
522 // this memory being no longer valid. (per the contract on
523 // reusing []byte between driver and user code). we only
524 // corrupt stuff from bytesClone, though, never the original
525 // copy of the data.
526 toCorrupt map[*byte]bool
527 } 520 }
528 521
529 func (rc *rowsCursor) Close() error { 522 func (rc *rowsCursor) Close() error {
530 if !rc.closed { 523 if !rc.closed {
531 » » for bp := range rc.toCorrupt { 524 » » for _, bs := range rc.bytesClone {
532 » » » *bp = 255 525 » » » bs[0] = 255 // first byte corrupted
533 } 526 }
534 } 527 }
535 rc.closed = true 528 rc.closed = true
536 return nil 529 return nil
537 } 530 }
538 531
539 func (rc *rowsCursor) Columns() []string { 532 func (rc *rowsCursor) Columns() []string {
540 return rc.cols 533 return rc.cols
541 } 534 }
542 535
543 func (rc *rowsCursor) Next(dest []interface{}) error { 536 func (rc *rowsCursor) Next(dest []interface{}) error {
544 if rc.closed { 537 if rc.closed {
545 return errors.New("fakedb: cursor is closed") 538 return errors.New("fakedb: cursor is closed")
546 } 539 }
547 rc.pos++ 540 rc.pos++
548 if rc.pos >= len(rc.rows) { 541 if rc.pos >= len(rc.rows) {
549 return io.EOF // per interface spec 542 return io.EOF // per interface spec
550 } 543 }
551 for i, v := range rc.rows[rc.pos].cols { 544 for i, v := range rc.rows[rc.pos].cols {
552 // TODO(bradfitz): convert to subset types? naah, I 545 // TODO(bradfitz): convert to subset types? naah, I
553 // think the subset types should only be input to 546 // think the subset types should only be input to
554 // driver, but the sql package should be able to handle 547 // driver, but the sql package should be able to handle
555 // a wider range of types coming out of drivers. all 548 // a wider range of types coming out of drivers. all
556 // for ease of drivers, and to prevent drivers from 549 // for ease of drivers, and to prevent drivers from
557 // messing up conversions or doing them differently. 550 // messing up conversions or doing them differently.
558 dest[i] = v 551 dest[i] = v
559 552
560 if bs, ok := v.([]byte); ok { 553 if bs, ok := v.([]byte); ok {
561 » » » if rc.toCorrupt == nil { 554 » » » if rc.bytesClone == nil {
562 » » » » rc.toCorrupt = make(map[*byte]bool)
563 rc.bytesClone = make(map[*byte][]byte) 555 rc.bytesClone = make(map[*byte][]byte)
564 } 556 }
565 clone, ok := rc.bytesClone[&bs[0]] 557 clone, ok := rc.bytesClone[&bs[0]]
566 if !ok { 558 if !ok {
567 clone = make([]byte, len(bs)) 559 clone = make([]byte, len(bs))
568 copy(clone, bs) 560 copy(clone, bs)
569 rc.bytesClone[&bs[0]] = clone 561 rc.bytesClone[&bs[0]] = clone
570 } 562 }
571 rc.toCorrupt[&clone[0]] = true
572 dest[i] = clone 563 dest[i] = clone
573 } 564 }
574 } 565 }
575 return nil 566 return nil
576 } 567 }
577 568
578 func converterForType(typ string) driver.ValueConverter { 569 func converterForType(typ string) driver.ValueConverter {
579 switch typ { 570 switch typ {
580 case "bool": 571 case "bool":
581 return driver.Bool 572 return driver.Bool
582 case "int32": 573 case "int32":
583 return driver.Int32 574 return driver.Int32
584 case "string": 575 case "string":
585 return driver.String 576 return driver.String
586 } 577 }
587 panic("invalid fakedb column type of " + typ) 578 panic("invalid fakedb column type of " + typ)
588 } 579 }
LEFTRIGHT

Powered by Google App Engine
RSS Feeds Recent Issues | This issue
This is Rietveld f62528b