CRC-16 チェックサム計算

複数のCRC-16アルゴリズムをサポートするCRC-16循環冗長検査計算ツール

CRC-8・CRC-32にも対応した汎用CRC計算ツールを開く

ツール概要:CRC-16 チェックサム計算ツール

CRC-16(16ビット循環冗長検査)は、データ送信と保存における整合性検証に主に使用される広く使用されているエラー検出アルゴリズムです。このツールは、さまざまなアプリケーションシナリオに適した複数のCRC-16アルゴリズム変種をサポートしています。

CRC-16 チェックサム計算ツールとは?

CRC-16 チェックサム計算ツールはエンコード/デコードやチェックサム生成に対応します。

使い方

  1. 内容を貼り付けるかテキストを入力します。
  2. エンコード/ハッシュ方式を選択します。
  3. 結果をコピーします。

よくある利用シーン

  • 署名や整合性チェック
  • システム間の安全な転送
  • デバッグ時の簡易検証

❓ よくある質問

Q1: 同じ入力で結果が違う?
A: エンコードと不可視文字を確認してください。

Q2: 逆変換できる?
A: エンコードは可能、ハッシュは不可です。

Q3: 大きな入力は?
A: 小分け処理を推奨します。

🔧 サポートされているアルゴリズム

CRC-16 Standard

  • 多項式: 0x8005 (x^16 + x^15 + x^2 + 1)
  • 初期値: 0x0000
  • 用途: 一般的なデータ検証

CRC-16 CCITT

  • 多項式: 0x1021 (x^16 + x^12 + x^5 + 1)
  • 初期値: 0xFFFF
  • 用途: 通信プロトコル、X.25、HDLC

CRC-16 Modbus

  • 多項式: 0x8005
  • 初期値: 0xFFFF
  • 用途: Modbus通信プロトコル

CRC-16 XMODEM

  • 多項式: 0x1021
  • 初期値: 0x0000
  • 用途: XMODEMファイル転送プロトコル

💡 使用例

1. データ整合性検証

// データ送信整合性チェック
class DataIntegrityChecker {
  constructor() {
    this.checksums = new Map();
  }

  // データのCRC-16チェックサムを計算して保存
  storeChecksum(dataId, data) {
    const crc16 = this.calculateCRC16(data, 'crc16');
    this.checksums.set(dataId, crc16);
    return crc16;
  }

  // データ整合性を検証
  verifyIntegrity(dataId, currentData) {
    const originalCRC = this.checksums.get(dataId);
    if (!originalCRC) {
      return { valid: false, reason: '元のチェックサムが見つかりません' };
    }

    const currentCRC = this.calculateCRC16(currentData, 'crc16');
    const isValid = originalCRC === currentCRC;

    return {
      valid: isValid,
      originalCRC: '0x' + originalCRC.toString(16).toUpperCase(),
      currentCRC: '0x' + currentCRC.toString(16).toUpperCase(),
      reason: isValid ? 'データは完全です' : 'データが変更されています'
    };
  }

  calculateCRC16(data, algorithm) {
    // 実際の実装では専門的なCRCライブラリを使用
    return this.crcCalculate(data, algorithm);
  }
}

// 使用例
const checker = new DataIntegrityChecker();

// 元のデータのチェックサムを保存
const originalData = "重要なビジネスデータ";
const checksum = checker.storeChecksum('data001', originalData);
console.log('保存されたチェックサム:', checksum);

// データ整合性を検証
const currentData = "重要なビジネスデータ"; // 未変更
const verification = checker.verifyIntegrity('data001', currentData);
console.log('整合性検証結果:', verification);

2. 通信プロトコル実装

// Modbus通信プロトコルCRC検証
class ModbusProtocol {
  constructor() {
    this.crcTable = this.generateCRCTable(0x8005);
  }

  // CRCルックアップテーブルを生成
  generateCRCTable(polynomial) {
    const table = [];
    for (let i = 0; i < 256; i++) {
      let crc = i;
      for (let j = 0; j < 8; j++) {
        if (crc & 1) {
          crc = (crc >>> 1) ^ polynomial;
        } else {
          crc = crc >>> 1;
        }
      }
      table[i] = crc & 0xFFFF;
    }
    return table;
  }

  // Modbus CRC-16を計算
  calculateModbusCRC(data) {
    let crc = 0xFFFF;
    const bytes = typeof data === 'string' ? 
      new TextEncoder().encode(data) : data;

    for (const byte of bytes) {
      const tableIndex = (crc ^ byte) & 0xFF;
      crc = ((crc >>> 8) ^ this.crcTable[tableIndex]) & 0xFFFF;
    }

    return crc;
  }

  // Modbusメッセージフレームを作成
  createFrame(deviceId, functionCode, data) {
    const frame = [deviceId, functionCode, ...data];
    const crc = this.calculateModbusCRC(new Uint8Array(frame));
    
    // CRCをリトルエンディアン形式でフレーム末尾に追加
    frame.push(crc & 0xFF);
    frame.push((crc >>> 8) & 0xFF);
    
    return new Uint8Array(frame);
  }

  // Modbusメッセージフレームを検証
  verifyFrame(frame) {
    if (frame.length < 4) {
      return { valid: false, reason: 'フレーム長が不足しています' };
    }

    const dataLength = frame.length - 2;
    const data = frame.slice(0, dataLength);
    const receivedCRC = frame[dataLength] | (frame[dataLength + 1] << 8);
    const calculatedCRC = this.calculateModbusCRC(data);

    return {
      valid: receivedCRC === calculatedCRC,
      receivedCRC: '0x' + receivedCRC.toString(16).toUpperCase(),
      calculatedCRC: '0x' + calculatedCRC.toString(16).toUpperCase(),
      reason: receivedCRC === calculatedCRC ? 'CRC検証が通過しました' : 'CRC検証が失敗しました'
    };
  }
}

// 使用例
const modbus = new ModbusProtocol();

// 保持レジスタ読み取りリクエストフレームを作成
const frame = modbus.createFrame(0x01, 0x03, [0x00, 0x00, 0x00, 0x02]);
console.log('Modbusフレーム:', Array.from(frame).map(b => '0x' + b.toString(16).toUpperCase()));

// 受信したフレームを検証
const verification = modbus.verifyFrame(frame);
console.log('フレーム検証結果:', verification);

🔍 アルゴリズムの特徴

利点

  • 高速計算: MD5、SHAアルゴリズムより高速
  • ハードウェアフレンドリー: ハードウェア実装が容易
  • 標準化: 複数の標準アルゴリズムが利用可能
  • リアルタイム性: リアルタイムデータ検証に適している

制限事項

  • セキュリティ: 暗号学的セキュリティには不適切
  • 衝突: 異なるデータが同じチェックサムを持つ可能性
  • 長さ: 16ビットチェックサムは比較的短い

⚠️ 使用推奨事項

  1. アルゴリズム選択: 特定のプロトコルに基づいて適切なCRC-16変種を選択
  2. パフォーマンス最適化: ルックアップテーブルを使用して計算効率を向上
  3. エラー処理: 包括的なエラー検出と処理を実装
  4. テスト検証: 標準テストベクトルを使用して実装の正確性を検証

📚 技術参考資料

  • ITU-T V.41: CCITT CRC-16標準
  • Modbus仕様: Modbus CRC-16実装
  • RFC 1662: PPPでのCRC-16使用
  • ISO 3309: HDLCでのCRC標準