Merge pull request #1050 from JerryFoundation/v5-dev

1. 在使用阻塞等待获取锁的方式中,必须在try代码块之外,并且在加锁方法与try代码块之间没有任何可能抛出异常的方法调用,避免加锁成功后…
This commit is contained in:
Golden Looly 2020-08-29 17:42:32 +08:00 committed by GitHub
commit cf1c96592c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 303 additions and 290 deletions

View File

@ -105,7 +105,7 @@ public class ConcurrentHashSet<E> extends AbstractSet<E> implements java.io.Seri
@Override @Override
public boolean remove(Object o) { public boolean remove(Object o) {
return map.remove(o) == PRESENT; return PRESENT.equals(map.remove(o));
} }
@Override @Override

View File

@ -16,73 +16,86 @@ import java.util.concurrent.TimeoutException;
* @author loolly * @author loolly
*/ */
public class DelegatedExecutorService extends AbstractExecutorService { public class DelegatedExecutorService extends AbstractExecutorService {
private final ExecutorService e; private final ExecutorService e;
DelegatedExecutorService(ExecutorService executor) { DelegatedExecutorService(ExecutorService executor) {
e = executor; e = executor;
} }
@SuppressWarnings("NullableProblems") @Override
public void execute(Runnable command) { @SuppressWarnings("NullableProblems")
e.execute(command); public void execute(Runnable command) {
} e.execute(command);
}
public void shutdown() { @Override
e.shutdown(); public void shutdown() {
} e.shutdown();
}
@SuppressWarnings("NullableProblems") @Override
public List<Runnable> shutdownNow() { @SuppressWarnings("NullableProblems")
return e.shutdownNow(); public List<Runnable> shutdownNow() {
} return e.shutdownNow();
}
public boolean isShutdown() { @Override
return e.isShutdown(); public boolean isShutdown() {
} return e.isShutdown();
}
public boolean isTerminated() { @Override
return e.isTerminated(); public boolean isTerminated() {
} return e.isTerminated();
}
@SuppressWarnings("NullableProblems") @Override
public boolean awaitTermination(long timeout, TimeUnit unit) throws InterruptedException { @SuppressWarnings("NullableProblems")
return e.awaitTermination(timeout, unit); public boolean awaitTermination(long timeout, TimeUnit unit) throws InterruptedException {
} return e.awaitTermination(timeout, unit);
}
@SuppressWarnings("NullableProblems") @Override
public Future<?> submit(Runnable task) { @SuppressWarnings("NullableProblems")
return e.submit(task); public Future<?> submit(Runnable task) {
} return e.submit(task);
}
@SuppressWarnings("NullableProblems") @Override
public <T> Future<T> submit(Callable<T> task) { @SuppressWarnings("NullableProblems")
return e.submit(task); public <T> Future<T> submit(Callable<T> task) {
} return e.submit(task);
}
@SuppressWarnings("NullableProblems") @Override
public <T> Future<T> submit(Runnable task, T result) { @SuppressWarnings("NullableProblems")
return e.submit(task, result); public <T> Future<T> submit(Runnable task, T result) {
} return e.submit(task, result);
}
@SuppressWarnings("NullableProblems") @Override
public <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks) throws InterruptedException { @SuppressWarnings("NullableProblems")
return e.invokeAll(tasks); public <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks) throws InterruptedException {
} return e.invokeAll(tasks);
}
@SuppressWarnings("NullableProblems") @Override
public <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit) @SuppressWarnings("NullableProblems")
throws InterruptedException { public <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit)
return e.invokeAll(tasks, timeout, unit); throws InterruptedException {
} return e.invokeAll(tasks, timeout, unit);
}
@SuppressWarnings("NullableProblems") @Override
public <T> T invokeAny(Collection<? extends Callable<T>> tasks) @SuppressWarnings("NullableProblems")
throws InterruptedException, ExecutionException { public <T> T invokeAny(Collection<? extends Callable<T>> tasks)
return e.invokeAny(tasks); throws InterruptedException, ExecutionException {
} return e.invokeAny(tasks);
}
public <T> T invokeAny(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit) @Override
throws InterruptedException, ExecutionException, TimeoutException { public <T> T invokeAny(Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit)
return e.invokeAny(tasks, timeout, unit); throws InterruptedException, ExecutionException, TimeoutException {
} return e.invokeAny(tasks, timeout, unit);
}
} }

View File

@ -20,255 +20,255 @@ import java.util.concurrent.locks.ReentrantReadWriteLock;
* @author Looly * @author Looly
*/ */
public class TaskTable implements Serializable { public class TaskTable implements Serializable {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
private final ReadWriteLock lock = new ReentrantReadWriteLock(); private final ReadWriteLock lock = new ReentrantReadWriteLock();
private final Scheduler scheduler; private final Scheduler scheduler;
private final TimeZone timezone; private final TimeZone timezone;
private final List<String> ids = new ArrayList<>(); private final List<String> ids = new ArrayList<>();
private final List<CronPattern> patterns = new ArrayList<>(); private final List<CronPattern> patterns = new ArrayList<>();
private final List<Task> tasks = new ArrayList<>(); private final List<Task> tasks = new ArrayList<>();
private int size; private int size;
/** /**
* 构造 * 构造
* *
* @param scheduler {@link Scheduler} * @param scheduler {@link Scheduler}
*/ */
public TaskTable(Scheduler scheduler) { public TaskTable(Scheduler scheduler) {
this.scheduler = scheduler; this.scheduler = scheduler;
this.timezone = scheduler.getTimeZone(); this.timezone = scheduler.getTimeZone();
} }
/** /**
* 新增Task * 新增Task
* *
* @param id ID * @param id ID
* @param pattern {@link CronPattern} * @param pattern {@link CronPattern}
* @param task {@link Task} * @param task {@link Task}
* @return this * @return this
*/ */
public TaskTable add(String id, CronPattern pattern, Task task) { public TaskTable add(String id, CronPattern pattern, Task task) {
final Lock writeLock = lock.writeLock(); final Lock writeLock = lock.writeLock();
try { writeLock.lock();
writeLock.lock(); try {
if (ids.contains(id)) { if (ids.contains(id)) {
throw new CronException("Id [{}] has been existed!", id); throw new CronException("Id [{}] has been existed!", id);
} }
ids.add(id); ids.add(id);
patterns.add(pattern); patterns.add(pattern);
tasks.add(task); tasks.add(task);
size++; size++;
} finally { } finally {
writeLock.unlock(); writeLock.unlock();
} }
return this; return this;
} }
/** /**
* 获取所有ID返回不可变列表即列表不可修改 * 获取所有ID返回不可变列表即列表不可修改
* *
* @return ID列表 * @return ID列表
* @since 4.6.7 * @since 4.6.7
*/ */
public List<String> getIds() { public List<String> getIds() {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
return Collections.unmodifiableList(this.ids); return Collections.unmodifiableList(this.ids);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 获取所有定时任务表达式返回不可变列表即列表不可修改 * 获取所有定时任务表达式返回不可变列表即列表不可修改
* *
* @return 定时任务表达式列表 * @return 定时任务表达式列表
* @since 4.6.7 * @since 4.6.7
*/ */
public List<CronPattern> getPatterns() { public List<CronPattern> getPatterns() {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
return Collections.unmodifiableList(this.patterns); return Collections.unmodifiableList(this.patterns);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 获取所有定时任务返回不可变列表即列表不可修改 * 获取所有定时任务返回不可变列表即列表不可修改
* *
* @return 定时任务列表 * @return 定时任务列表
* @since 4.6.7 * @since 4.6.7
*/ */
public List<Task> getTasks() { public List<Task> getTasks() {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
return Collections.unmodifiableList(this.tasks); return Collections.unmodifiableList(this.tasks);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 移除Task * 移除Task
* *
* @param id Task的ID * @param id Task的ID
*/ */
public void remove(String id) { public void remove(String id) {
final Lock writeLock = lock.writeLock(); final Lock writeLock = lock.writeLock();
try { writeLock.lock();
writeLock.lock(); try {
final int index = ids.indexOf(id); final int index = ids.indexOf(id);
if (index > -1) { if (index > -1) {
tasks.remove(index); tasks.remove(index);
patterns.remove(index); patterns.remove(index);
ids.remove(index); ids.remove(index);
size--; size--;
} }
} finally { } finally {
writeLock.unlock(); writeLock.unlock();
} }
} }
/** /**
* 更新某个Task的定时规则 * 更新某个Task的定时规则
* *
* @param id Task的ID * @param id Task的ID
* @param pattern 新的表达式 * @param pattern 新的表达式
* @return 是否更新成功如果id对应的规则不存在则不更新 * @return 是否更新成功如果id对应的规则不存在则不更新
* @since 4.0.10 * @since 4.0.10
*/ */
public boolean updatePattern(String id, CronPattern pattern) { public boolean updatePattern(String id, CronPattern pattern) {
final Lock writeLock = lock.writeLock(); final Lock writeLock = lock.writeLock();
try { writeLock.lock();
writeLock.lock(); try {
final int index = ids.indexOf(id); final int index = ids.indexOf(id);
if (index > -1) { if (index > -1) {
patterns.set(index, pattern); patterns.set(index, pattern);
return true; return true;
} }
} finally { } finally {
writeLock.unlock(); writeLock.unlock();
} }
return false; return false;
} }
/** /**
* 获得指定位置的{@link Task} * 获得指定位置的{@link Task}
* *
* @param index 位置 * @param index 位置
* @return {@link Task} * @return {@link Task}
* @since 3.1.1 * @since 3.1.1
*/ */
public Task getTask(int index) { public Task getTask(int index) {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
return tasks.get(index); return tasks.get(index);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 获得指定id的{@link Task} * 获得指定id的{@link Task}
* *
* @param id ID * @param id ID
* @return {@link Task} * @return {@link Task}
* @since 3.1.1 * @since 3.1.1
*/ */
public Task getTask(String id) { public Task getTask(String id) {
final int index = ids.indexOf(id); final int index = ids.indexOf(id);
if (index > -1) { if (index > -1) {
return getTask(index); return getTask(index);
} }
return null; return null;
} }
/** /**
* 获得指定位置的{@link CronPattern} * 获得指定位置的{@link CronPattern}
* *
* @param index 位置 * @param index 位置
* @return {@link CronPattern} * @return {@link CronPattern}
* @since 3.1.1 * @since 3.1.1
*/ */
public CronPattern getPattern(int index) { public CronPattern getPattern(int index) {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
return patterns.get(index); return patterns.get(index);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 任务表大小加入的任务数 * 任务表大小加入的任务数
* *
* @return 任务表大小加入的任务数 * @return 任务表大小加入的任务数
* @since 4.0.2 * @since 4.0.2
*/ */
public int size() { public int size() {
return this.size; return this.size;
} }
/** /**
* 任务表是否为空 * 任务表是否为空
* *
* @return true为空 * @return true为空
* @since 4.0.2 * @since 4.0.2
*/ */
public boolean isEmpty() { public boolean isEmpty() {
return this.size < 1; return this.size < 1;
} }
/** /**
* 获得指定id的{@link CronPattern} * 获得指定id的{@link CronPattern}
* *
* @param id ID * @param id ID
* @return {@link CronPattern} * @return {@link CronPattern}
* @since 3.1.1 * @since 3.1.1
*/ */
public CronPattern getPattern(String id) { public CronPattern getPattern(String id) {
final int index = ids.indexOf(id); final int index = ids.indexOf(id);
if (index > -1) { if (index > -1) {
return getPattern(index); return getPattern(index);
} }
return null; return null;
} }
/** /**
* 如果时间匹配则执行相应的Task带读锁 * 如果时间匹配则执行相应的Task带读锁
* *
* @param millis 时间毫秒 * @param millis 时间毫秒
*/ */
public void executeTaskIfMatch(long millis) { public void executeTaskIfMatch(long millis) {
final Lock readLock = lock.readLock(); final Lock readLock = lock.readLock();
try { readLock.lock();
readLock.lock(); try {
executeTaskIfMatchInternal(millis); executeTaskIfMatchInternal(millis);
} finally { } finally {
readLock.unlock(); readLock.unlock();
} }
} }
/** /**
* 如果时间匹配则执行相应的Task无锁 * 如果时间匹配则执行相应的Task无锁
* *
* @param millis 时间毫秒 * @param millis 时间毫秒
* @since 3.1.1 * @since 3.1.1
*/ */
protected void executeTaskIfMatchInternal(long millis) { protected void executeTaskIfMatchInternal(long millis) {
for (int i = 0; i < size; i++) { for (int i = 0; i < size; i++) {
if (patterns.get(i).match(timezone, millis, this.scheduler.matchSecond)) { if (patterns.get(i).match(timezone, millis, this.scheduler.matchSecond)) {
this.scheduler.taskExecutorManager.spawnExecutor(tasks.get(i)); this.scheduler.taskExecutorManager.spawnExecutor(tasks.get(i));
} }
} }
} }
} }

View File

@ -140,8 +140,8 @@ public class RC4 implements Serializable {
*/ */
public byte[] crypt(final byte[] msg) { public byte[] crypt(final byte[] msg) {
final ReadLock readLock = this.lock.readLock(); final ReadLock readLock = this.lock.readLock();
readLock.lock();
byte[] code; byte[] code;
readLock.lock();
try { try {
final int[] sbox = this.sbox.clone(); final int[] sbox = this.sbox.clone();
code = new byte[msg.length]; code = new byte[msg.length];