gpt4 book ai didi

java - 这个 MessageDigest 包装器线程安全吗?

转载 作者:行者123 更新时间:2023-11-30 08:34:07 29 4
gpt4 key购买 nike

我自己编写了简化的 MessageDigest 包装器,现在我想知道它是否是线程安全的。

public final class SimpleIMD implements ImmutableMessageDigest {
private final MessageDigest md;

public SimpleIMD(MessageDigest md) {
this.md = this.cloneMessageDigest(md);
}

private MessageDigest cloneMessageDigest(MessageDigest original) {
MessageDigest clone = null;
try {
clone = (MessageDigest) original.clone();
} catch (CloneNotSupportedException cnse) {
throw new RuntimeException(
"Failed to instantiate a new SimpleImd instance.",
cnse
);
} finally {
return clone;
}
}

@Override
public byte[] digest() {
return this.md.digest();
}

@Override
public ImmutableMessageDigest update(byte[] arr, int offset, int len) {
MessageDigest newMsgDigest = this.cloneMessageDigest(this.md);
newMsgDigest.update(arr, offset, len);
return new SimpleIMD(newMsgDigest);
}
}

最佳答案

正如我所怀疑的,我的代码不是线程安全的。

例如,如果 2 个线程共享相同的 SimpleIMD 对象,并且方法调用的时间顺序将如下所示:

  T1                 T2
| |
update() |
| |
| digest()
| |
| |
| |

那么不能保证 update() 会在 digest() 之前完成。

事实上,digest() 甚至可以在 update()T1 之前重置底层的 MessageDigest 实例会有错误的散列。这个问题可以通过对新副本执行 digest() 来解决。

所以方法:

@Override
public byte[] digest() {
return this.md.digest();
}

必须更改为:

@Override
public byte[] digest() {
return this.cloneMessageDigest(this.md).digest();
}

更新

此处介绍的解决方案已纳入 ImmutableMessageDigest那是 Caesar 的一部分,我编写的一个开源库。

关于java - 这个 MessageDigest 包装器线程安全吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39049252/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com