push blocks until there is space available in the queue, and then adds job to the queue. If queue is closed or gets closed while waiting for space, push returns false.
(job chunkWriteJob)
| 65 | // push blocks until there is space available in the queue, and then adds job to the queue. |
| 66 | // If queue is closed or gets closed while waiting for space, push returns false. |
| 67 | func (q *writeJobQueue) push(job chunkWriteJob) bool { |
| 68 | q.mtx.Lock() |
| 69 | defer q.mtx.Unlock() |
| 70 | |
| 71 | // Wait until queue has more space or is closed. |
| 72 | for !q.closed && q.size >= q.maxSize { |
| 73 | q.popped.Wait() |
| 74 | } |
| 75 | |
| 76 | if q.closed { |
| 77 | return false |
| 78 | } |
| 79 | |
| 80 | // Check if this segment has more space for writing, and create new one if not. |
| 81 | if q.last == nil || q.last.nextWrite >= q.segmentSize { |
| 82 | prevLast := q.last |
| 83 | q.last = &writeJobQueueSegment{ |
| 84 | segment: make([]chunkWriteJob, q.segmentSize), |
| 85 | } |
| 86 | |
| 87 | if prevLast != nil { |
| 88 | prevLast.nextSegment = q.last |
| 89 | } |
| 90 | if q.first == nil { |
| 91 | q.first = q.last |
| 92 | } |
| 93 | } |
| 94 | |
| 95 | q.last.segment[q.last.nextWrite] = job |
| 96 | q.last.nextWrite++ |
| 97 | q.size++ |
| 98 | q.pushed.Signal() |
| 99 | return true |
| 100 | } |
| 101 | |
| 102 | // pop returns first job from the queue, and true. |
| 103 | // If queue is empty, pop blocks until there is a job (returns true), or until queue is closed (returns false). |