【问题标题】:Coding an enhanced LSB reverser编写增强的 LSB 反向器
【发布时间】:2013-09-04 22:54:50
【问题描述】:

我偶然发现了一个具有 12 个块(最后一个 LSB 略小)(.PNG)的分割 IDAT 结构的隐写图像。在谈到问题的真正意义之前,我将详细说明问题的结构,因为我需要澄清一些事情,所以请不要将其标记为离题,因为它不是。我只需要解释脚本背后的概念,以便我可以解决问题本身。它肯定将数据嵌入到自身中。数据似乎已通过更改增强的 LSB 值来隐藏,消除了每个像素的高级别位,除了最后一个最低有效位。所以所有字节都将是 0 或 1,因为 256 值范围上的 0 或 1 不会给出任何可见的颜色。基本上,0 保持在 0,1 变为最大值,即 255。我一直在以许多不同的方式分析这张图片,但除了三种颜色中的任何一种完全没有一个值之外,没有看到任何奇怪的地方值 (RGB) 和 1/3 颜色值中另一个值的高度存在。然而,研究这些和替换字节并没有给我任何东西,我不知道这条途径是否值得追求。

因此,我正在考虑使用 PythonPHPC/C++ 开发一个脚本,以逆转该过程并“恢复'增强的 LSB。

我已将其转换为24位.BMP并从卡方隐写分析追踪红色曲线,可以肯定存在隐写数据在文件中。

首先,垂直区域多于 8 个。这意味着隐藏的数据略多于 8kB。一个像素可用于隐藏三位(每个 RGB 色调的 LSB 中的一位)。所以我们可以隐藏 (98x225)x3 位。要获得千字节数,我们除以 8 再除以 1024:((98x225)x3)/(8x1024)。嗯,应该是 8.1 KB 左右。但这里不是这样。

.JPG 文件扩展名的 APPOAPP1 标记的分析也给出了一些尴尬的输出:

Start Offset: 0x00000000
*** Marker: SOI (xFFD8) ***
  OFFSET: 0x00000000

*** Marker: APP0 (xFFE0) ***
  OFFSET: 0x00000002
  length     = 16
  identifier = [JFIF]
  version    = [1.1]
  density    = 96 x 96 DPI (dots per inch)
  thumbnail  = 0 x 0

*** Marker: APP1 (xFFE1) ***
  OFFSET: 0x00000014
  length          = 58
  Identifier      = [Exif]
  Identifier TIFF = x[4D 4D 00 2A 00 00 00 08 ]
  Endian          = Motorola (big)
  TAG Mark x002A  = x[002A]

  EXIF IFD0 @ Absolute x[00000026]
    Dir Length = x[0003]
    [IFD0.x5110                          ] = 
    [IFD0.x5111                          ] = 0
    [IFD0.x5112                          ] = 0
    Offset to Next IFD = [00000000]

*** Marker: DQT (xFFDB) ***
  Define a Quantization Table.
  OFFSET: 0x00000050
  Table length = 67
  ----
  Precision=8 bits
  Destination ID=0 (Luminance)
    DQT, Row #0:   2   1   1   2   3   5   6   7 
    DQT, Row #1:   1   1   2   2   3   7   7   7 
    DQT, Row #2:   2   2   2   3   5   7   8   7 
    DQT, Row #3:   2   2   3   3   6  10  10   7 
    DQT, Row #4:   2   3   4   7   8  13  12   9 
    DQT, Row #5:   3   4   7   8  10  12  14  11 
    DQT, Row #6:   6   8   9  10  12  15  14  12 
    DQT, Row #7:   9  11  11  12  13  12  12  12 
    Approx quality factor = 94.02 (scaling=11.97 variance=1.37)

我几乎确信没有应用加密算法,因此隐藏后没有密钥实现。我的想法是编写一个脚本来改变 LSB 值并返回原始值。我已经在几个结构分析、统计攻击、BPCS、

图像的直方图显示了一种带有异常尖峰的特定颜色。我已经尽我所能尝试查看任何隐藏的数据,但无济于事。这些是 RGB 值的直方图,如下所示:

然后是多个 IDAT 块。但是,我通过在每个像素位置定义随机颜色值来组合一个类似的图像,我也总结了其中的几个。到目前为止,我在它们里面也发现了很少的东西。更有趣的是颜色值在图像中重复的方式。似乎,重复使用颜色的频率可以提供一些线索。但是,我还没有完全理解这种关系,如果存在的话。此外,只有单列和单行像素在其 Alpha 通道上不具有 255 的完整值。我什至已经解释了 XYARG ,以及图像中每个像素的 B 值作为 ASCII,但最终没有什么太清晰的内容。即使是 LSB 平均值的绿色曲线也无法告诉我们任何信息。没有明显的中断。以下是其他几个直方图,它们显示了 RGB 中蓝色值的奇怪曲线:

但是卡方分析的输出红色曲线显示出一些差异。它可以看到我们看不到的东西。统计检测比我们的眼睛更敏感,我想这是我的最后一点。但是,红色曲线中也存在某种延迟。即使没有隐藏数据,它也会以最大值开始并保持一段时间。这接近于误报。它看起来像图像中的 LSB,非常接近随机,并且该算法需要大量人口(请记住,分析是在增加的像素人口上完成的)才能达到可以确定它们实际上不是随机的阈值毕竟,红色曲线开始下降。隐藏数据也会出现同样的延迟。您隐藏了 1 或 2 kb,但在此数据量之后,红色曲线不会立即下降。它稍等片刻,分别在 1.3 kb 和 2.6 kb 左右。以下是十六进制编辑器中数据类型的表示:

byte = 166
signed byte = -90
word = 40,358
signed word = -25,178
double word = 3,444,481,446
signed double word = -850,485,850
quad = 3,226,549,723,063,033,254
signed quad = 3,226,549,723,063,033,254
float = -216652384.
double = 5.51490063721e-093
word motorola = 42,653
double word motorola = 2,795,327,181
quad motorola = 12,005,838,827,773,085,484

这是确认蓝色 (RGB) 值行为的另一个光谱。

请注意,我需要通过所有这些来澄清我所追求的情况和编程问题。这本身就使我的问题 NOT 偏离主题,所以如果它没有被标记为这样,我会很高兴。谢谢。

【问题讨论】:

  • 那么,你到底在问什么?
  • 我已经提过两次了,但我会再说一次。我可能需要将增强的 LSB 值反转回它们的原始状态,并且我需要自动执行这个过程,因此我需要想办法用 Python、C/C++ 或 PHP 来编码这个概念。
  • 对,所以你写了一个很长的问题描述,但我在你的帖子中没有看到直接的问题。我希望不是“请为我编写代码”,因为在这样的基础上结束问题会浪费很多精力。所以你能提出一个可以回答的真实问题吗?
  • 我需要找到一种方法来执行此操作 - 当然不是有人从头开始为我编写代码。我知道这是一种方式。如果有人可以指导我如何实现这一目标,我很乐意自己编写代码,但到目前为止我没有任何想法。
  • 所以,你基本上是在问“编码是如何完成的,我该如何反转它?”

标签: c++ python image-processing steganography


【解决方案1】:

如果图像应用了 LSB 增强,我想不出办法将其恢复到原始状态,因为不知道 RGB 的原始值。根据它们的最低有效位,它们被设置为 255 或 0。我在这里看到的另一个选项是,如果这是某种包含量子隐写术的协议。

Matlab 和一些隐写分析技术可能是解决问题的关键。

这是一个用于一些统计分析的 Java 卡方类:

private long[] pov = new long[256];
and three methods as

public double[] getExpected() {
        double[] result = new double[pov.length / 2];
        for (int i = 0; i < result.length; i++) {
            double avg = (pov[2 * i] + pov[2 * i + 1]) / 2;
            result[i] = avg;
        }
        return result;
}
public void incPov(int i) {
        pov[i]++;
}
public long[] getPov() {
        long[] result = new long[pov.length / 2];
        for (int i = 0; i < result.length; i++) {
            result[i] = pov[2 * i + 1];
        }
        return result;

或尝试一些按位移位操作:

int pRGB = image.getRGB(x, y);
int alpha = (pRGB >> 24) & 0xFF;
int blue = (pRGB >> 16) & 0xFF;
int green = (pRGB >> 8) & 0xFF;
int red = pRGB & 0xFF;

【讨论】:

  • 没有。上面的卡方正是来自这个 Java 源代码和另一个用 python 编码的。如果是量子隐写术,那一切都是徒劳的,我注定要失败..
  • 关键是你的图像中有相当多的噪声,这让我相信它要么是增强的 LSB 值(你已经正确排除了)要么是量子技术。否则,我无法确定它还能是什么。
  • “将量子信息隐藏在通过信道的量子纠错码的码字中”。这意味着我不能(不可能)仅通过监控频道的权力进行窃听,但没有密钥,无法将消息与频道噪音区分开来。换句话说,除了这个之外,肯定还有其他的东西。
  • 另外,'noise' 不仅仅指文件的视觉表示。它可能与十六进制转储或其他有关;任何不可读/损坏的数据作为一个整体。
猜你喜欢
  • 2020-01-15
  • 2012-11-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-04-05
  • 1970-01-01
相关资源
最近更新 更多