Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.
View | Details | Raw Unified | Return to bug 211799 | Differences between
and this patch

Collapse All | Expand All

(-)src/org/eclipse/core/internal/jobs/InternalJob.java (+22 lines)
Lines 89-94 Link Here
89
	 * or -1 if the job should not be rescheduled.
89
	 * or -1 if the job should not be rescheduled.
90
	 */
90
	 */
91
	private long startTime;
91
	private long startTime;
92
	
93
	/**
94
	 * Stamp added when a job is added to the wait queue. Used to ensure
95
	 * jobs in the wait queue maintain their insertion order even if they are
96
	 * removed from the wait queue temporarily while blocked
97
	 */
98
	private long waitQueueStamp = T_NONE;
99
	
92
	/*
100
	/*
93
	 * The thread that is currently running this job
101
	 * The thread that is currently running this job
94
	 */
102
	 */
Lines 538-541 Link Here
538
	protected void wakeUp(long delay) {
546
	protected void wakeUp(long delay) {
539
		manager.wakeUp(this, delay);
547
		manager.wakeUp(this, delay);
540
	}
548
	}
549
550
	/**
551
	 * @param waitQueueStamp The waitQueueStamp to set.
552
	 */
553
	void setWaitQueueStamp(long waitQueueStamp) {
554
		this.waitQueueStamp = waitQueueStamp;
555
	}
556
557
	/**
558
	 * @return Returns the waitQueueStamp.
559
	 */
560
	long getWaitQueueStamp() {
561
		return waitQueueStamp;
562
	}
541
}
563
}
(-)src/org/eclipse/core/internal/jobs/JobManager.java (-2 / +11 lines)
Lines 127-132 Link Here
127
	 */
127
	 */
128
	private final JobQueue waiting;
128
	private final JobQueue waiting;
129
129
130
	/**
131
	 * Counter to record wait queue insertion order.
132
	 */
133
	private long waitQueueCounter;
134
130
	public static void debug(String msg) {
135
	public static void debug(String msg) {
131
		StringBuffer msgBuf = new StringBuffer(msg.length() + 40);
136
		StringBuffer msgBuf = new StringBuffer(msg.length() + 40);
132
		if (DEBUG_TIMING) {
137
		if (DEBUG_TIMING) {
Lines 319-324 Link Here
319
			switch (newState) {
324
			switch (newState) {
320
				case Job.NONE :
325
				case Job.NONE :
321
					job.setStartTime(InternalJob.T_NONE);
326
					job.setStartTime(InternalJob.T_NONE);
327
					job.setWaitQueueStamp(InternalJob.T_NONE);
322
				case InternalJob.BLOCKED :
328
				case InternalJob.BLOCKED :
323
					break;
329
					break;
324
				case Job.WAITING :
330
				case Job.WAITING :
Lines 334-339 Link Here
334
				case Job.RUNNING :
340
				case Job.RUNNING :
335
				case InternalJob.ABOUT_TO_RUN :
341
				case InternalJob.ABOUT_TO_RUN :
336
					job.setStartTime(InternalJob.T_NONE);
342
					job.setStartTime(InternalJob.T_NONE);
343
					job.setWaitQueueStamp(InternalJob.T_NONE);
337
					running.add(job);
344
					running.add(job);
338
					break;
345
					break;
339
				case InternalJob.ABOUT_TO_SCHEDULE :
346
				case InternalJob.ABOUT_TO_SCHEDULE :
Lines 433-440 Link Here
433
	 */
440
	 */
434
	private void doSchedule(InternalJob job, long delay) {
441
	private void doSchedule(InternalJob job, long delay) {
435
		synchronized (lock) {
442
		synchronized (lock) {
436
			//if it's a decoration job, don't run it right now if the system is busy
443
			//if it's a decoration job with no rule, don't run it right now if the system is busy
437
			if (job.getPriority() == Job.DECORATE) {
444
			if (job.getPriority() == Job.DECORATE && job.getRule() == null) {
438
				long minDelay = running.size() * 100;
445
				long minDelay = running.size() * 100;
439
				delay = Math.max(delay, minDelay);
446
				delay = Math.max(delay, minDelay);
440
			}
447
			}
Lines 443-448 Link Here
443
				changeState(job, Job.SLEEPING);
450
				changeState(job, Job.SLEEPING);
444
			} else {
451
			} else {
445
				job.setStartTime(System.currentTimeMillis() + delayFor(job.getPriority()));
452
				job.setStartTime(System.currentTimeMillis() + delayFor(job.getPriority()));
453
				job.setWaitQueueStamp(waitQueueCounter++);
446
				changeState(job, Job.WAITING);
454
				changeState(job, Job.WAITING);
447
			}
455
			}
448
		}
456
		}
Lines 828-833 Link Here
828
			InternalJob job = sleeping.peek();
836
			InternalJob job = sleeping.peek();
829
			while (job != null && job.getStartTime() < now) {
837
			while (job != null && job.getStartTime() < now) {
830
				job.setStartTime(now + delayFor(job.getPriority()));
838
				job.setStartTime(now + delayFor(job.getPriority()));
839
				job.setWaitQueueStamp(waitQueueCounter++);
831
				changeState(job, Job.WAITING);
840
				changeState(job, Job.WAITING);
832
				job = sleeping.peek();
841
				job = sleeping.peek();
833
			}
842
			}
(-)src/org/eclipse/core/internal/jobs/JobQueue.java (-1 / +20 lines)
Lines 72-78 Link Here
72
		Assert.isTrue(newEntry.previous() == null);
72
		Assert.isTrue(newEntry.previous() == null);
73
		InternalJob tail = dummy.next();
73
		InternalJob tail = dummy.next();
74
		//overtake lower priority jobs. Only overtake conflicting jobs if allowed to
74
		//overtake lower priority jobs. Only overtake conflicting jobs if allowed to
75
		while (tail != dummy && tail.compareTo(newEntry) < 0 && (allowConflictOvertaking || !newEntry.isConflicting(tail)))
75
		while (canOvertake(newEntry, tail))
76
			tail = tail.next();
76
			tail = tail.next();
77
		//new entry is smaller than tail
77
		//new entry is smaller than tail
78
		final InternalJob tailPrevious = tail.previous();
78
		final InternalJob tailPrevious = tail.previous();
Lines 83-88 Link Here
83
	}
83
	}
84
84
85
	/**
85
	/**
86
	 * Returns whether the new entry to overtake the existing queue entry.
87
	 * @param newEntry The entry to be added to the queue
88
	 * @param queueEntry The existing queue entry
89
	 */
90
	private boolean canOvertake(InternalJob newEntry, InternalJob queueEntry) {
91
		//can never go past the end of the queue
92
		if (queueEntry == dummy)
93
			return false;
94
		//if the new entry was already in the wait queue, ensure it is re-inserted in correct position (bug 211799)
95
		if (newEntry.getWaitQueueStamp() > 0 && newEntry.getWaitQueueStamp() < queueEntry.getWaitQueueStamp())
96
			return true;
97
		//if the new entry has lower priority, there is no need to overtake the existing entry
98
		if (queueEntry.compareTo(newEntry) >= 0)
99
			return false;
100
		//the new entry has higher priority, but only overtake the existing entry if the queue allows it
101
		return allowConflictOvertaking || !newEntry.isConflicting(queueEntry);
102
	}
103
104
	/**
86
	 * Removes the given element from the queue. 
105
	 * Removes the given element from the queue. 
87
	 */
106
	 */
88
	public void remove(InternalJob toRemove) {
107
	public void remove(InternalJob toRemove) {

Return to bug 211799