Firmware

Version.1系とVersion.3系の違い

HULのリリース当時から2021年7月まで保守を続けてきたファームウェア(version.1)とそれ以降のファームウェア(version.3)ではBCTの仕様変更に伴いソフトウェアに互換性がありません。 Version.2系はver.3系へアップデートする際の内部開発系統なので公開していません。 Version.1ではBCTでRBCP addressの一部をデータ線として使っていましたが、version.3ではRBCP address 32 bitとRBCP data 8 bitをそのまま利用するようにしています。 ソフトウェアでもModuleIDとLocalAddressによる表記をやめ、RBCP addressでローカルモジュールを指定するように変更しました。 ModuleIDやLocalAddressはlocal bus controllerの構造を知らないユーザーにとっては不必要な情報であるためです。

Version.3系では全てのファームウェアの共通機能として2つのローカルモジュールが追加されました。SiTCP経由でSPI flash memoryを書き換えるFlash Memory Programmer (FMP)、およびFPGAや基板の状態を自己診断するSelf Diagnosis System (SDS)です。FMPのおかげでUSBブラスターケーブルを使って書き込んでいたMCSファイルをネットワーク経由でダウンロードすることが出来るようになりました。これにより遠隔でのファームウェア更新が可能となりました。SDSは放射線によるソフトエラー修正回数の監視、および修復不可能な状態に落ちった事の検出が可能です。また、FPGAの温度、およびVCCINT、VCCAUX、VCCBRAM電位の監視が可能です。

ファームウェアの基本構造

HULのファームウェアには大別するとデータ収集を担うTDCのようなタイプと、トリガー回路のようなデータをPCへ転送しないタイプが存在します。 後者は機能によってブロック構成が異なりますが、データ収集タイプのファームウェアは統一されたブロック構造を持ちます。 以下にデータ収集タイプのブロック図を示します。 図中オレンジで示した構成要素はどのファームウェアにも実装されている機能です。 各ローカルモジュールを制御するlocal busはlocal bus controller (BCT)によって制御されており、BCTはSiTCPのRBCP (UDP)と接続されています。 FMPとSDSは全てのversion.3系のファームウェアに実装されているローカルモジュールであり、機能は前述の通りです。

データ収集に関わる部分は図中の白い四角で表されています。 TDCやスケーラといった計測に関わるブロックは計測ブロックと呼ばれます。 それらの機能は主にuser circuitと書かれたブロックに実装されます。 これらuser circuitからのデータはbuilder busを介してevent builderブロックに集められ、イベントヘッダを付与した後SiTCPを通じてPCへ転送されます。 Receiver block、trigger manager、およびJ0 interfaceはトリガー入出力に関わるブロックです。 HULはMTM (GNN-570)から送信されてくるトリガーとイベントタグ情報を受け取るように設計されています。 Receiver blockはHRMメザニンカードが実装されている場合有効になるブロックであり、トリガーを上流の回路から受け取る役割を持ちます。 このブロックはトリガー受信と同時に受信したトリガー情報をPCへ転送するためにbuilder busにも接続されています。 Receiver blockを利用するHULはVMEクレート内のJ0バスマスタであると思われます。 J0 interfaceはHULがJ0バスマスタである場合、receiver blockが受け取ったトリガーとタグ情報をJ0バスへ流します。 一方J0バスに対してスレイブである場合、J0バスからやってきたトリガー情報をtrigger managerへ渡します。 また、HULは汎用モジュールであるため、MTMが存在しない状況でも利用できるようにNIMポートからのトリガー入力をサポートしています。 Trigger managerはファームウェア内部のトリガー配布を担っており、HRMメザニン (receiver block)、NIM入力、J0バス入力からトリガー入力経路を選択できます。 Trigger managerが送信するLEVEL2Fast clearTAGの情報はevent builder内部でデータ送信の決定やイベントヘッダ情報の生成に利用されます。

daqtype-block

各ファームウェア共通の事柄

hul_softwareは共通部分であるBCT、FMP、およびSDSのアドレスをcommon/src/RegisterMapCommon.hhで管理しています。

リセットシーケンス

2017年12月19日づけの更新分から各ファームウェアのリセットシーケンスを統一しました。 これまでのファームウェアではBCTがハングアップするとリセットする手段が電源OFF以外なかったり、MH-TDCではBCTリセットをかけても一部FIFOの状態がリセットされず、DAQがハングしている状態が解除されなかったり、という問題がありました。 そこで、リセットのレベルを段階ごとに設定して対処できるようにしました。

リセット方法(下に行くほど影響範囲が広いです)

  • BCTリセット:BCTのResetにRBCPで書き込みを行う。BCT管理下にあるユーザーモジュールがリセットされる。通常のリセット。
  • SiTCPリセット:sitcp_controller.ccのReset_SiTCPを呼び出す。BCTがハングしている場合でもリセット可能。BCTもデッドロック状態から復帰する。
  • ハードリセット:基板上のSW3を押す。SiTCPを含む全回路がリセットされる。最も強制力がある。

通常はBCTリセットを利用し、操作を誤ってBCTがデッドロックした場合はSiTCPリセットを、SiTCPがハングしてしまった場合はハードリセットを、という順番で利用してください。

サポートするネットワーク規格

現在公開しているファームウェアでは、SiTCPはGbEでしか動作しないようになっています。 SiTCP自体は100 MbpsとGbEの両方をサポートし自動切り替えが可能なのですが、利用しているPHYの都合で自動切り替えの機能を意図的に利用不可にしています。 100 Mbpsで利用する要求はほぼないだろうと思っているので100 Mbpsのバージョンは作成していません。 100 Mbpsでしか通信できないネットワークスイッチにつなぐとSiTCPが動かなくなります。

Bus controller

BCTにはローカルモジュールにアクセスする機能のほかに、BCTリセットを発行する、バージョンを取得する、FPGAの再コンフィグを行う、という機能が実装されています。 これらの機能はRBCP addressで以下のアドレスを実行することで利用可能です。 BCTに対してVersion読み出しを行うと32bitのレジスタが返ってきます。 このうち上位16bitがFirmware固有名で、下位16bitがバージョン (メジャーバージョン 8bit + マイナーバージョン 8bit) となります。 以下の表においてビット幅が-と表記されているレジスタについては、送信レジスタ値の内容を気にしません。 書き込み動作を行うことで効力が発揮されます。

RBCP address of BCT (Module ID: 0xE)

レジスタ名 アドレス 読み書き ビット幅 備考
Reset 0xE000'0000 W - Bus Controllerからモジュールリセット信号をアサートし、SiTCPを除く全モジュールを初期化。
Version 0xE010'0000 R 32 Firmwareの固有名とバージョンを読み出す。多バイト読み出しが必要。
Reconfig 0xE020'0000 W - PROG_B_ONをLowにしてFPGAの再コンフィギュレーションを行う。一度通信が切れるので暫くしてから再接続。

Flash Memory Programmer

FMPはPCから指定したSPIコマンドを送信することでメモリがサポートしているコマンドの実行、ページデータの読み書きが可能です。 メモリの消去、書き込み、読み出しをFMPを通じて行う事が可能であり、Vivadoを通じてメモリへ書き込む動作(消去、書き込み、ベリファイ)と同じことがネットワークを通じて実行可能です。

FMPには既知のバグがあります。ページ書き込みをする際に書き込みコマンドを実行してからそのコマンドが終了する前に次のページ書き込みを要求できてしまいます。 現状はファームウェア側で対処せずにソフトウェア側で十分な時間待って次のページ書き込みコマンドを送信するようにしていますが、あまり良い対処方法ではありません。 そのうちファームウェア側で根本対処するかもしれません。 このような対処を行っているため、ネットワークで書き込みを行っている割には時間がかかります。 書き込みに失敗する事象が頻発する場合、著者へ連絡をしてください。

以下にRBCPアドレスを記載しますが、hul_softwareに同梱されているFlashMemoryProgrammer.cc以外からFMPを制御するのはお勧めしません。 間違って書き込みロックビットを立ててしまうと、そのメモリには二度と書き込みが出来なくなります。

RBCP address of FMP (Module ID: 0xD)

レジスタ名 アドレス 読み書き ビット幅 備考
Status 0xD000'0000 R 8 FMPモジュールのステータスビットを取得します。
現状下位1ビットにSPIコマンドサイクルbusyが割り当てられています。
Status 0xD000'0000 R/W 8 SPIシーケンスのモード切替を行います。
1~2-bit目: SPIシーケンスモード
  • 0x0: Read mode
  • 0x1: Write mode
  • 0x2: Instruction mode
3-bit目: Dummy mode
Chip selectをOFFにし、SPIシーケンスを回してもフラッシュメモリが反応しないようにします。
Register 0xD020'0000 R/W 64 SPIコマンドのビット列を与えます。
InstLength 0xD030'0000 R/W 3 SPIコマンドのビット長を与えます。
ReadLength 0xD040'0000 R/W 10 ページ読み出し長を与えます。
WriteLength 0xD050'0000 R/W 10 ページ書き込み長を与えます。
ReadCountFIFO 0xD060'0000 R 10 ページ読み出ししたデータが格納されているFIFOのread countを取得します。
ReadFIFO 0xD070'0000 R 8 8-bitずつページ読み出しFIFOからデータ読み出します。
WriteCountFIFO 0xD080'0000 R 10 ページ書き込み用のデータを格納するFIFOのwrite countを取得します。
WriteFIFO 0xD090'0000 W 8 8-bitずつページ書き込み用FIFOへデータを書き込みます。
Execute 0xD100'0000 W - SPIコマンドシーケンスを実行します。

Self Diagnosis System

SDSは自己診断プログラムです。 Xilinx FPGAのIPであるSoft Error Mitigation (SEM)とXADCをそれぞれ実体化し監視しています。 SEMはsingle event upset (SEU)を検知、訂正、分類するIPです。 SDSでは訂正可能なエラーを訂正した回数の取得と、訂正不可能なエラーが発生したことの検知が行えます。 訂正不可能な状態に陥った場合フラッシュメモリからFPGAを再コンフィグするか、パワーサイクルを行う必要があります。 また、意図的にSEUをインジェクトすることが可能ですが、SDSの高度な利用になるのでSEMの利用方法をXilinxのUGで調べて使用してください。

XADCはXilinx FPGAのビルトインADCです。 HULではXADCを利用してFPGAの温度、およびVCCINT、VCCAUX、VCCBRAM電位を取得しています。

SEMには未解決のトラブルがあります。 FPGAの個体によっては電源投入後にuncorrectable errorステータスが1になってしまいます。 原因は分かっていませんが一度SEMをリセットすることで正常に使う事が出来ます。 そのような個体に遭遇したら電源投入後にhul_softwareのreset_semを実行してください。

RBCP address of SDS (Module ID: 0xC)

レジスタ名 アドレス 読み書き ビット幅 備考
SdsStatus 0xC000'0000 R 8 SDSモジュールのステータスを取得します。
XadcDrpMode 0xC010'0000 R/W 1 XADCのDRPモード選択をします。
  • 0x0: Read mode
  • 0x1: Write mode
XadcDrpAddr 0xC020'0000 R/W 7 XADCのDRP addressを与えます。
XadcDrpDin 0xC030'0000 R/W 16 XADCのDRPのデータ入力を与えます。
XadcDrpDout 0xC040'0000 R 16 XADCのDRPのデータ出力を取得します。
XadcExecute 0xC0F0'0000 W - XADCのDRPアクセスを実行します。
SemCorCount 0xC100'0000 R 16 訂正可能なSEUをSEMが訂正した回数を取得します。
SemRstCorCount 0xC200'0000 W - SemCorCountをリセットします。
SemErroAddr 0xC300'0000 W 40 SEMのinject_addressポートに入力するアドレスを与えます。
SemErroStrobe 0xC400'0000 W - SEMのinject_strobeポートにパルスを入力します。

SdsStatusの内容

ビット番号 ステータス名 備考
1 Over temp FPGA温度が125℃を超えたことを示します。重大な冷却不足なので直ぐにHULの電源を切り冷やしてください。
2 Temp alarm FPGA温度が85℃を超えたことを示します。冷却能力が不足していることが考えられます。
3 VCCINT alarm VCCINTの電圧が正常範囲 (0.97-1.03V) を超えたことを示しています。何らかのトラブルが基板に起きています。
4 未使用
5 Watchdog alarm SEMのheartbeat信号が出ていない事を示します。何らかのトラブルがSEMに起きています。
6 Uncorrectable error SEMのが訂正不可能な放射線エラーを検出したことを示します。FPGAの再コンフィグが必要です。
7 未使用
8 未使用

HUL Skeleton

このプロジェクトはSiTCPを実装しつつ何もしないfirmwareのほぼ最小構成になります。HUL用のfirmwareを作る際のサンプルとして使ってください。機能は2つしかなく、入力信号をORしてNIMで出力する機能と、SiTCPもしくはDIPでLEDを光らせる機能です。信号のORでは固定入力とメザニン入力(DCRv1かv2を想定)をコネクタ単位でOR(32 OR)して、それぞれ4つのNIMOUTから出力します。

Skeletonの綴りが間違っているのですが直すと影響範囲が広いのでこのままにします。

NIM-Exメザニンカードを利用する際のイグザンプルがsources_1/example_design/以下に同梱してあります。 同梱されたtoplevel.vhdを参考にしてください。

Firmware固有名と現在の最新版

現在のHUL Skeletonの固有名とバージョンは以下のようになります。

固有名 0x0000
メジャーバージョン 0x03
マイナーバージョン 0x02

以下バージョンはv3.2のような形式で表記します。

更新歴

バージョン リリース日 変更点
- - v2.xまでの履歴は無し
v3.2 2021.08.01 Version.3系へ変更。

レジスタマップ

RBCP address of LED (Module ID: 0x0)

LED点灯のパターン
LED1-3はLEDレジスタかもしくはSW2の2-4ビット目で点灯させることが出来ます。 LED4番目はSDSのover temperatureフラグが接続されています。

HUL RM

HUL RMはmezzanine HRMをマウントすることにより、J0バスマスタとなることができ、なおかつHRMが受信したデータを読み出すDAQモジュールとして動作させることができます。MH-TDCやscalerファームウェアの元となる構成をしており、新しくDAQタイプのファームウェアを開発する際の出発点として利用してください。

Trigger入力に対しる応答はこのファームウェアが基本となっているため、ここではtrigger系統とそれに対するevent builderの応答について詳しく説明します。

Firmware固有名と現在の最新版

固有名 0x0415
メジャーバージョン 0x03
マイナーバージョン 0x02

更新歴

バージョン リリース日 変更点
v1.0 2016.12.23 初期版
v1.1 2017.01.15 RVMのデータヘッダを0x9Cから0xF9へ変更。
v1.2 2017.01.27 Vivado更新 2016.2 => 2016.4 TRM の中間バッファを分散RAMからBRAMへ変更。深さを128から256に変更Prog Full threshold導入。256に設定した理由はSCRブロックの深さを越えないようにするため。それにあわせて、RVMの中間バッファ深さを256へ変更。見かけの機能に変更は無し。
v1.3 2017.03.22 IOMの初期レジスタが正しく設定できていない問題を解決。電源投入後最初のイベントでヘッダ2に書かれているワード数が0になってしまう問題を解決。
v1.4 2017.05.09 Clearに応答しない(BUSYが立ちっぱなしになる)問題を解決。
v1.5 HRMを使っていて尚且つClearが入るとハングする問題を解決。(リリースしないままv1.6にとってかわった。)
v1.6 2017.08.22 トリガーが入って2 us程度以内にハードリセットが入るとDAQがハングする問題を修正。ハードリセットへ応答するかどうか、ブロックごとにレジスタで設定できるように変更。新しいローカルアドレス追加。
v1.7 2017.12.19 リセットシーケンスを統一。Header3の24ビット目にHRMが刺さっているかどうか(正確にはDIP2がONかどうか)を示すビットを挿入。
v1.8 2018.02.02 J0バスからやってくるイベントタグをラッチするタイミングが早すぎて、HRM側のイベント番号と1ずれるバグを解決。
v2.x - 未公開
v3.2 2021.08.01 FMPとSDSを追加。Builder busの導入。Local busの構造変更。

モジュール動作概要
HUL RMのデータ収集に関わるブロック図を以下に示します。この図ではデータ収集に関わるモジュール以外は省略しています。HUL RMの機能はMezzanine HRMが受信、およびデコードした情報の処理です。そのため、mezzanine slot Uにのみ機能が実装されています。Mezzanine HRMが受信した情報は3つの経路に分配されます。1つはReceiver Module (RVM) であり、lock bit、spill number increment、spill number (full 8bit)、event number (full 12bit) の情報を記憶し、event builder (EVB) に渡します。Event builderへはbuilder busを介してデータが渡されるため、RVMの情報はデータボディに含まれます。すなわち、RVMはEVBに取って計測ブロックの一部です。2つ目の経路はJ0 busへのトリガー情報の配布です。この段階でevent numberは3-bitへspill numberは1-bitへ減らされます。3つ目はTRMへの入力になります。

HULのファームウェアには内部のトリガー配布を管理するtrigger manager (TRM) というモジュールが存在します。TRMは3つのポート、trig Ext (NIM IN)、J0 bus (スレーブの場合)、およびHRM (存在する場合) からトリガー信号を受け取ることができ、どのポートから受け取るかはレジスタで設定します。

TRMはlevel1 trigger, level2 trigger, clear, およびevent number (3-bit)、spill number (1-bit)の情報を各計測ブロックとEVBへ配布します。EVBにとってはこれらはDAQデータではないので、event hearder内にTRMからのタグは埋め込まれます。HULがJ0 busに対してマスターである場合とスレーブである場合とで情報を同等に取り扱わないといけないので、TRMが配布するevent numberとspill numberは3-bitと1-bitに減らされています。Tagを受け取っていない場合event numberもspill numberも0になります。

I/O ManagerはNIM入力ポートをどのFPGA内部信号に割り当てるか、またFPGA内部の信号をNIM出力ポートに割り当てるかを制御するモジュールです。

HULには3種類のbusy信号が存在します。 1つ目はmodule busyであり、これはファームウェア内部のブロックが出力するbusy信号の論理和です。 2つ目はj0 bus busy信号であり、これはJ0 busに対してスレーブなHULのmodule busy信号の論理和です。通常J0 busに対してマスターであるHULが取り扱います。 最後はcrarte busy信号であり、これはmodule busy、J0 bus busy、およびNIM-INポートから入力される外部busy信号の論理和です。これも通常J0 busに対してマスターであるHULが取り扱います。

rm-fw

レジスタマップ

以下はHUL RM専用のマップです。同名のモジュールやレジスタが他のファームウェアに存在しても同一のアドレスであるとは限りません。必ずこのマップ (もしくは配布したソフトウェアのRegisterMap.hh及びnamespace) にしたがって設定してください。

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: TRM (module ID = 0x00)
SelectTrigger 0x0000'0000 R/W 12 TRM内部のトリガーポートの選択を行うレジスタ。
DAQ Controller: DCT (module ID = 0x01)
DaqGate 0x1000'0000 R/W 1 DAQ gateのON/OFF。DAQ gateが0だとTRMはtriggerを出力できない。
EvbReset 0x1010'0000 W - このアドレスへ書き込み要求することでEVBのソフトリセットがアサートされ、Event builder内部のセルフイベントカウンタが0になる。
IO Manager: IOM (module ID = 0x02)
NimOut1 0x2000'0000 R/W 4 NIMOUT1へ何を出力するかを設定する。
NimOut2 0x2010'0000 R/W 4 NIMOUT2へ何を出力するかを設定する。
NimOut3 0x2020'0000 R/W 4 NIMOUT3へ何を出力するかを設定する。
NimOut4 0x2030'0000 R/W 4 NIMOUT4へ何を出力するかを設定する。
ExtL1 0x2040'0000 R/W 3 extL1にどのNIMINを接続するか設定。
ExtL2 0x2050'0000 R/W 3 extL2にどのNIMINを接続するか設定。
ExtClr 0x2060'0000 R/W 3 Ext clearにどのNIMINを接続するか設定。
ExtBusy 0x2070'0000 R/W 3 Ext busy入力にどのNIMINを接続するか設定。
ExtRsv2 0x2080'0000 R/W 3 Ext rsv2入力にどのNIMINを接続するか設定。

Trigger Manager (TRM)
TRMはどの入力ポートからの信号をトリガーとして使うのかを決め、FPGA内部用のL1、L2、Clear信号を出力します。また、Tagを受けとっている場合FPGA内部で使うために再配布します。どのポートの信号を選択するかは12-bitのレジスタ、SelectTriggerで設定します。トリガー信号の経路とSelectTriggerの関係をにまとめます。L1 triggerをどのポートから受けるかは3つのbitで決まります。2つ以上のbitをセットするとトリガーがORで入ってきてしまいます。L1の経路が決まると次にDAQ gate (DAQ controller管理) とのANDをとり、L1 triggerとして配布されます。L2 triggerとClearの選択も同様に3つのbitで行いますが、これらは経路決定後にEnL2 bitの影響を受けます。EnL2が0の場合L2にはL1のコピーが送信され、Clearは常に0です。MTM-RMシステムを使わない簡易はDAQを行う場合このbitを0にします。その後、L2もDAQ gateとのANDをとり配布されます。Tag情報はJ0から受け取るのかHRMから受け取るのかをEnJ0とEnRM bitsで選択します。両方1にするとTagが出力されません。

trm-block

TRM::SelectTriggerアドレスに対するレジスタ値のリストです。それぞれのビットが該当するセレクタのスイッチになっているので、このレジスタは整数値ではなく12-bit幅のビット列になります。例外的にRegEnJ0のみTRMの外でも使われます。RegEnJ0がhighであり、かつDIP SW2 2番 (mezzanine HRM) がlowの場合に限り、J0 busへmodule busyを流します。クレートにモジュールを挿入するがJ0 busへは影響を与えたくない場合はこのレジスタをlowにします。

レジスタラベル レジスタ値 備考
RegL1Ext 0x1 NIMINからL1 triggerを選択。
RegL1J0 0x2 J0 busからのL1 triggerを選択。
RegL1RM 0x4 Mezzanine HRMからのL1 triggerを選択。
RegL2Ext 0x8 NIMINからのL2 triggerを選択。
RegL2J0 0x10 J0 busからのL2 triggerを選択。
RegL2RM 0x20 Mezzanine HRMからのL2 triggerを選択。
RegClrExt 0x40 NIMINからのClearを選択。
RegClrJ0 0x80 J0 busからのClearを選択。
RegClrRM 0x100 Mezzanine HRMからのClearを選択。
RegEnL2 0x200 0: L2=L1 trigger、1: L2=L2入力
RegEnJ0 0x400 Tag情報にJ0 busの物を採用する。また、このbitが1だとJ0 busへ自身のmodule busyを流す。
RegEnRM 0x800 Tag情報にHRMから受信した値を採用する。

I/O Manager (IOM)
IOMはFPGA内部の信号をNIMOUTへ割り当てたり、NIMINの信号をFPGA内部の信号線へ接続したりする機能を持ちます。たとえば、以下で述べるAddrNnimout1へReg_o_ModuleBusyを設定した場合、フロントパネルのNIM出力1番からmodule busy信号が出力されます。AddrExtL1へReg_i_Nimin1を設定した場合、TRMのL1Ext線にNIM入力1番が割り当てられます。割り当てることの出来るレジスタを以下にまとめます。NIM出力は、出力するNIMポートのアドレスに信号線のレジスタを設定する、NIM入力は内部の信号線のアドレスへNIM入力ポートのレジスタを設定すると、逆の関係になっています。これらのレジスタ値はビット列ではなく整数値として解釈します。

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_ModuleBusy 0x0 Module busyです。Module busyは自身の内部busyのみを指します。J0 busのbusyやExtBusyは含まれません。
Reg_o_CrateBusy 0x1 CrateBusyです。CrateBusyはmodule busyに加えてJ0 busのbusyやExtBusyを含みます。J0 busマスタの場合に利用する信号になり、またHRMが Trigger Moduleへ返すbusyと同等です。
Reg_o_RML1 0x2 HRMが受信したL1 triggerを出力します。
Reg_o_RML2 0x3 HRMが受信したL2 triggerを出力します。
Reg_o_RMClr 0x4 HRMが受信したClearを出力します。
Reg_o_RMRsv1 0x5 HRMが受信したReserve 1を出力します。
Reg_o_RMSnInc 0x6 HRMがSpill Number Incrementを出力します。
Reg_o_DaqGate 0x7 DAQ gateを出力します。
Reg_o_DIP8 0x8 DIP SW2の8-bit目で設定したレベルを出力します。
Reg_o_clk1MHz 0x9 1 MHzのクロックを出力します。
Reg_o_clk100kHz 0xA 100 kHzのクロックを出力します。
Reg_o_clk10kHz 0xB 10 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
内部信号線へ割り当て可能なNIMINポート
Reg_i_nimin1 0x0 NIMIN1番を信号線へアサインします。
Reg_i_nimin2 0x1 NIMIN2番を信号線へアサインします。
Reg_i_nimin3 0x2 NIMIN3番を信号線へアサインします。
Reg_i_nimin4 0x3 NIMIN4番を信号線へアサインします。
Reg_i_default 0x7 このレジスタが設定された場合、指定のデフォルト値がそれぞれの内部信号線へ代入されます。

IOMには初期割り当てが存在します。その初期値を以下に列挙します。

NIM出力ポート 初期レジスタ
NIMOUT1 Reg_o_ModuleBusy
NIMOUT2 reg_o_DaqGate
NIMOUT3 reg_o_clk1kHz
NIMOUT4 reg_o_DIP8
内部信号線 初期レジスタ デフォルト値
ExtL1 Reg_i_nimin1 NIMIN1
ExtL2 Reg_i_default 0
ExtLClear Reg_i_default 0
ExtLBusy Reg_i_nimin3 NIMIN3
ExtLRsv2 Reg_i_nimin4 NIMIN4

HUL上のスイッチ・LEDの機能

DIP SW2の機能

スイッチ番号 機能 詳細
1 SiTCP force default ONでSiTCPのデフォルトモードで起動します。電源投入前に設定している必要があります。
2 Mezzanine HRM ONでMezzanine HRMをマウントするためのモードになります。このビットにより切り替わる機能については後述します。このビットがデータのHeader3に現れます。
3 Force BUSY Crate BusyとModule Busyを強制的にHighにします。接続チェックなどに使ってください。
4 Bus BUSY ONでCrate BusyにJ0 bus busyを含め、OFFで含めません。
5 LED ONでLED4番を光らせます。
6 Not in Use
7 Not in Use
8 Level IOMのDIP8から出力されるレベルです。

Mezzanine HRM (DIP SW2) の機能
DIP SW2の2-bit目がONになるとMezzanine HRMにかかわる複数の機能が切り替わります。

Event BuilderがRVMをイベントパケットに含める
RVMの情報をEvent Builderが読み出してイベントパケットに含めるようになります。

Mezzanine base Uの入出力方向の変更
ONでMezzanine HRMにあわせていくつかの信号線がLVDS出力に切り替わります。OFF状態では全ての線はLVDS入力で接続されます。

J0 busマスタモードをOnにする
このビットがONだと、J0 busへL1, L2, Clear, Tag情報を流すようになり、なおかつJ0 busに流れるBUSY信号を受け取ることが出来るようになります。ただし、同時にDIP SW1を全てONにしている必要があります。

J0 busスレーブモードをOFFにする
このビットがOFFだと、J0 busからL1, L2, Clear, Tagを受け取らなくなります。また、BUSY信号をJ0 busへ流しません。

以下がJ0 bus信号線とトリガー信号の関係です。

J0 bus信号線 トリガー信号線
S1 RM_Clear
S2 RM_Level2
S3 RM_SpillNumber(0)
S4 RM_Level1
S5 RM_EventNumber(0)
S6 RM_EventNumber(1)
S7 RM_EventNumber(2)

LED点灯の機能

LED番号 備考
LED1 点灯中はTCP接続が張られています。
LED2 点灯中はmodule busyがhighです。
LED3 点灯中はDIP SW2のMezzanine HRMがONであることを意味します。
LED4 点灯中はDIP SW2のLEDがONです。

DAQの動作

データフローとDAQの動作について述べます。DAQ機能は各計測用モジュール (以下計測ブロック) とevent builderモジュールによって構成されます。データフローをに示します。トリガーを受信すると各計測ブロックは決められた動作に従いデータを処理してブロックバッファに保存します。計測ブロックは内部にブロックバッファを持ち、マルチイベントを一時的に保存できるようになっています。Event builderは各計測ブロックからデータを読み、イベントバッファがfullでない限りイベントビルドを続けます。そのため、DAQ機能がトリガーに対して同期して動くのはブロックバッファにデータを書き込むまでであり、それから後段の処理は外界の信号や状態に依存せずデータリンクスピードが許す限りビルドと転送を続けます。

HUL RMの場合計測ブロックはRVMとTRMのみなります。TRMの情報はデータボディには含まれずヘッダに含まれるため厳密にはTRMは計測ブロックではありません。イベントビルトされる情報はRVMデータのみであり、TRMの情報はデータの転送制御に使われます。TRMはN番目のイベントにL2 triggerとClearのどちらが送信されたかを保存しており、この情報を使ってevent builderはN番目のイベントパケットをSiTCPに送るか、それともそのまま破棄するかを決定します。そのため、HULのDAQ機能には実質的にはfast clearという動作がなく、clear busyという物も存在しません。L1 riggerによって発生したイベントは必ずビルドされます。ただし、event builderが付与するセルフイベント番号は転送が行われない限りインクリメントされません。

RVMはL2 triggerのタイミングでに示した情報をラッチしてブロックバッファに保存します。

daq-rm-fw

Module Busyとなるタイミング
HUL RMのmodule busyの定義は以下に列挙するbusy信号のORになります。Block fullとSiTCP fullはネットワーク転送が追いつかなくなる限り発生しないため、通常は160 nsの固定長BUSYのみとなります。現在self-busyに160 nsが設定されていますが、若干長めのため将来的に短くする可能性があります。

BUSY種別 BUSY長 備考
Self busy 160 ns L1 triggerを検出した瞬間から固定長でアサート。
Block full - ブロックバッファがfullになった段階でbusyが出力されます。L1 triggerレートが後段の回路のデータ処理速度を上回るとアサートされます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。
SiTCP full - SiTCPのTCPバッファがfullになると出力されます。ネットワークスピードに対してevent builderが送信しようとするデータ量が多いとアサートされます。

データ構造
HULでは32-bitを1ワードとして、3ワードのヘッダと可変長のデータボディを1イベントのブロックとしています。
Header word

Header1 (Magic word)
MSB                                                                                          LSB
|                                           0xFFFF0415                                         |

Header2 (event size)
|       0xFF       |      0x00       |    "00000"    |         Number of word (11-bit)         |

"Number of word" はデータボディに何ワード含まれるかを示します。ヘッダの3ワードは含みません。

Header3 (event number)
|       0xFF       | HRM exist | "000" | Tag (4-bit) |         Self counter (16-bit)           |

HRM existが1の場合HRMメザニンカードが取り付けられていることを示します。すなわち、データボディにRVMのデータワードが存在します。 TagはTRMから受信した4-bitのタグ情報です。下位3ビットがMTMが送信したイベントナンバーの下位3ビットに相当し、4ビット目がスピルナンバーの最下位ビットです。 Self counterはイベントが送信されるたびにインクリメントされるローカルイベント番号です。0から始まります。

Data body

RVM word
|  0xF9   | "00"  | Lock  | SNI  | Spill Num (8-bit) |            Event Num (12-bit)           |

LockはHRMのlock bitです。1でないといけません。SNIはspill number incrementであり、1であればスピル番号が変わったことを示しますが、そのように動作しているかどうかはチェックしていません。 Spill NumEvent NumはそれぞれHRMが受信したスピルナンバーとイベントナンバーです。

HUL Scaler

HUL ScalerはHUL RMの機能にスケーラを追加したファームウェアです。実装したスケーラは300 MHzでサンプリングを行う、28-bitの同期カウンタです。HUL ScalerはHUL RMと多くの機能が共通のため、異なる点のみ述べます。

Firmware固有名と現在の最新版

固有名 0x4ca1
メジャーバージョン 0x03
マイナーバージョン 0x03

更新歴

バージョン リリース日 変更点
v1.0 2016.12.23 初期版
v1.1 2017.01.15 RVMのデータヘッダを0x9Cから0xF9へ変更。
v1.2 2017.01.27 Vivado更新 2016.2 => 2016.4 TRM の中間バッファを分散RAMからBRAMへ変更。深さを128から256に変更Prog Full threshold導入。256に設定した理由はSCRブロックの深さを越えないようにするため。それにあわせて、RVMの中間バッファ深さを256へ変更。見かけの機能に変更は無し。
v1.3 2017.03.22 IOMの初期レジスタが正しく設定できていない問題を解決。電源投入後最初のイベントでヘッダ2に書かれているワード数が0になってしまう問題を解決。
v1.4 2017.05.09 Clearに応答しない(BUSYが立ちっぱなしになる)問題を解決。
v1.5 HRMを使っていて尚且つClearが入るとハングする問題を解決。(リリースしないままv1.6にとってかわった。)
v1.6 2017.08.22 トリガーが入って2 us程度以内にハードリセットが入るとDAQがハングする問題を修正。ハードリセットへ応答するかどうか、ブロックごとにレジスタで設定できるように変更。新しいローカルアドレス追加。
v1.7 2017.12.19 リセットシーケンスを統一。Header3の24ビット目にHRMが刺さっているかどうか(正確にはDIP2がONかどうか)を示すビットを挿入。
v1.8 2018.02.02 J0バスからやってくるイベントタグをラッチするタイミングが早すぎて、HRM側のイベント番号と1ずれるバグを解決。
v2.x - 未公開
v3.3 2021.08.01 FMPとSDSを追加。Builder busの導入。Local busの構造変更。

モジュール動作概要
HUL ScalerではHRMで動作未定義となっていた残りのMezzanine slot Dと固定入力ポートに機能が割り当てられています。Mezzanine slotにはDCR v1 (v2)を実装することを想定しており、最大128ch分のスケーラ値を取得することができます。また、Mezzanine slot UにはDCRの代わりにHRMをマウントすることでHUL RMと同様J0 busマスタになることも可能です。この場合slot Uに割り当てられている32ch分は強制的にデータから削除されます。

Scalerは300 MHz、28-bit長のカウンタで構成されており、L1 triggerのタイミングでカウンタをラッチしてバッファへ書き込みます。HUL scalerでは2つ新しい内部信号がIOMに接続されています。1つはspill gateで、この信号がhighの間のみスケーラはカウントアップします。もう1つはcounter resetで、highになったタイミングでカウンタ値を全てリセットします。NIM入力のカウンターリセットに応答するかどうかは、enable_hdrstで設定可能です (v1.6以降)。他の機能はHUL RMと同様になります。

scaler-fw

レジスタマップ

以下のテーブルはHUL Scaler専用のレジスタです。同名のモジュールやレジスタが他のfirmwareに存在しても同一のアドレスであるとは限りません。必ずこのマップ (もしくは配布したソフトウェアのRegisterMap.hh及びnamespace) にしたがって設定してください。 HUR RMの異なる部分は赤字で示してあります。

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: TRM (module ID = 0x00)
SelectTrigger 0x0000'0000 R/W 12 TRM内部のトリガーポートの選択を行うレジスタ。
DAQ Controller: DCT (module ID = 0x01)
DaqGate 0x1000'0000 R/W 1 DAQ gateのON/OFF。DAQ gateが0だとTRMはtriggerを出力できない。
EvbReset 0x1010'0000 W - このアドレスへ書き込み要求することでEVBのソフトリセットがアサートされ、Event builder内部のセルフイベントカウンタが0になる。
IO Manager: SCR (module ID = 0x02)
CounterReset 0x2000'0000 W - Software counter resetをアサート。
EnableBlock 0x2010'0000 R/W 4 どのブロック (入力ポート毎) を利用するか設定。ビットをhighにするとそのブロックのデータが取得できるようになります。入力ポートと対応するビットは
1bit目:Main in U
2bit目:Main in D
3bit目:Mezzanine U
4bit目:Mezzanine D
EnableHdrst 0x2020'0000 R/W 4 NIM入力のhardware counter resetに応答するかどうかをブロックごとに設定します。ビットが1でそのブロックはhardware counter resetのタイミングでカウンタが0に戻ります。入力ポートと対応するビットは
1bit目:Main in U
2bit目:Main in D
3bit目:Mezzanine U
3bit目:Mezzanine U
IO Manager: IOM (module ID = 0x03)
NimOut1 0x3000'0000 R/W 4 NIMOUT1へ何を出力するかを設定する。
NimOut2 0x3010'0000 R/W 4 NIMOUT2へ何を出力するかを設定する。
NimOut3 0x3020'0000 R/W 4 NIMOUT3へ何を出力するかを設定する。
NimOut4 0x3030'0000 R/W 4 NIMOUT4へ何を出力するかを設定する。
ExtL1 0x3040'0000 R/W 3 extL1にどのNIMINを接続するか設定。
ExtL2 0x3050'0000 R/W 3 extL2にどのNIMINを接続するか設定。
ExtClr 0x3060'0000 R/W 3 Ext clearにどのNIMINを接続するか設定。
ExtSpillGate 0x3070'0000 R/W 3 内部信号線のext spill gateにどのNIMINを接続するか設定。
ExtCCRst 0x3080'0000 R/W 3 内部信号線のext counter resetにどのNIMINを接続するのか設定。
ExtBusy 0x3090'0000 R/W 3 Ext busy入力にどのNIMINを接続するか設定。
ExtRsv2 0x30A0'0000 R/W 3 Ext rsv2入力にどのNIMINを接続するか設定。

各ブロックの機能

Trigger Manager (TRM)
機能およびレジスタはHUL RMと同様です。

Scaler (SCR)
スケーラはHUL Scalerの主機能になります。各スケーラユニットは300 MHzで入力信号を同期し、その後エッジ検出を行い、そのエッジのタイミングでカウンタを1つインクリメントします。そのため、検出可能なパルスの最小幅は3.5~4.0 ns程度で、なおかつ2つのパルスを分離するためにも同程度パルスが離れている必要があります。カウンタは28-bit長で一周すると0に戻ります。スケーラは32chごとに4つのブロックに分けられており、EnableBlockレジスタで利用するブロックを設定できます。対応するビットがhighであればそのブロック全体 (32ch分)のデータが返ってきて、lowであれば32ch全て返ってきません。スケーラのリセットはハードリセットのExtCounterReset(NIMIN、IOMで制御)、もしくはソフトリセットのCounterResetアサートによって行うことが出来ます。ハードリセットに応答するかどうかはEnableHdrstでブロックごとに設定できます。このビットが1のブロックはハードリセットのタイミングでカウンタが0になります。また、トリガーから前後100 nsにリセットが入った場合の動作は不定とします。データは返ってきますが、意図しない値が入っているかもしれません。

スケーラのインクリメントはExtSpillGate (NIMIN、IOMで制御) によって制御できます。スケーラはspill gateがhighの時だけインクリメントされます。Spill gateはNIM入力ポートを割り当てると利用することが出来ます。もし未割り当ての場合デフォルトで常にhighになるように設定されています。

I/O Manager (IOM)
IOMの機能はHUL RMと基本的に同様ですが、ExtSpillGateとExtCCRstへのNIMINポートの割り当てが追加されています。NIMOUT側は変更ありません。

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_ModuleBusy 0x0 Module busyです。Module busyは自身の内部busyのみを指します。J0 busのbusyやExtBusyは含まれません。
Reg_o_CrateBusy 0x1 CrateBusyです。CrateBusyはmodule busyに加えてJ0 busのbusyやExtBusyを含みます。J0 busマスタの場合に利用する信号になり、またHRMが Trigger Moduleへ返すbusyと同等です。
Reg_o_RML1 0x2 HRMが受信したL1 triggerを出力します。
Reg_o_RML2 0x3 HRMが受信したL2 triggerを出力します。
Reg_o_RMClr 0x4 HRMが受信したClearを出力します。
Reg_o_RMRsv1 0x5 HRMが受信したReserve 1を出力します。
Reg_o_RMSnInc 0x6 HRMがSpill Number Incrementを出力します。
Reg_o_DaqGate 0x7 DAQ gateを出力します。
Reg_o_DIP8 0x8 DIP SW2 8番のレベルを出力します。
Reg_o_clk1MHz 0x9 1 MHzのクロックを出力します。
Reg_o_clk100kHz 0xA 100 kHzのクロックを出力します。
Reg_o_clk10kHz 0xB 10 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
内部信号線へ割り当て可能なNIMINポート
Reg_i_nimin1 0x0 NIMIN1番を信号線へアサインします。
Reg_i_nimin2 0x1 NIMIN2番を信号線へアサインします。
Reg_i_nimin3 0x2 NIMIN3番を信号線へアサインします。
Reg_i_nimin4 0x3 NIMIN4番を信号線へアサインします。
Reg_i_default 0x7 このレジスタが設定された場合、指定のデフォルト値がそれぞれの内部信号線へ代入されます。

以下はIOMレジスタの初期値のテーブルです。

NIM出力ポート 初期レジスタ
NIMOUT1 Reg_o_ModuleBusy
NIMOUT2 reg_o_DaqGate
NIMOUT3 reg_o_clk1kHz
NIMOUT4 reg_o_DIP8
内部信号線 初期レジスタ デフォルト値
ExtL1 Reg_i_Nimin1 NIMIN1
ExtL2 Reg_i_default 0
ExtLClear Reg_i_default 0
ExtSpillGate Reg_i_default 1
ExtCounterReset Reg_i_nimin2 NIMIN2
ExtLBusy Reg_i_nimin3 NIMIN3
ExtLRsv2 Reg_i_nimin4 NIMIN4

HUL上のスイッチ・LEDの機能

DIP SW2の機能
HUL RMと同様です。

LED点灯の機能
HUL RMと同様です。

DAQの動作

データフローをに示します。HUL RMにSCRが追加され、DIP SW2のmezzanine HRMがOFFであればSCRのみからデータを集め、mezzanine HRMがONであればSCRとRVM両方からデータを集めてイベントビルドします。ヘッダ2のnumber of wordにはSCRとRVMの合計ワード数が入ります。

daq-scaler-fw

Module Busyとなるタイミング
HUL Scalerのmodule BUSYの定義は以下に列挙するBUSY信号のORになります。Block fullとSiTCP fullはネットワーク転送が追いつかなくなる限り発生しないため、通常は210 nsの固定長BUSYのみとなります。現在Self-busyに210 nsが設定されていますが、若干長めのため将来的に短くする可能性があります。HUL RMとSelf-busyの長さが異なるのは使っているシステムクロックの周波数が異なるためです。

BUSY種別 BUSY長 備考
Self busy 210 ns L1 triggerを検出した瞬間から固定長でアサート。
Block full - ブロックバッファがfullになった段階でBUSYが出力されます。L1 triggerレートが後段の回路のデータ処理速度を上回るとアサートされます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。
SiTCP full - SiTCPのTCPバッファがFullになると出力されます。ネットワーク帯域に対してEvent Builderが送信しようとするデータ量が多いとアサートされます。

データ構造
Header word

Header1 (Magic word)
MSB                                                                                          LSB
|                                           0xFFFF4CA1                                         |

Header2 (event size)
|       0xFF       |      0x00       |    "00000"    |         Number of word (11-bit)         |

Number of wordはデータボディに何ワード含まれるかを示します。ヘッダの3ワードは含みません。

Header3 (event number)
|       0xFF       | HRM exist | "000" | Tag (4-bit) |         Self counter (16-bit)           |

HRM existが1の場合HRMメザニンカードが取り付けられていることを示します。すなわち、データボディにRVMのデータワードが存在します。 TagはTRMから受信した4-bitのタグ情報です。下位3ビットがMTMが送信したイベントナンバーの下位3ビットに相当し、4ビット目がスピルナンバーの最下位ビットです。 Self counterはイベントが送信されるたびにインクリメントされるローカルイベント番号です。0から始まります。

Data body

RVM word
|  0xF9   | "00"  | Lock  | SNI  | Spill Num (8-bit) |            Event Num (12-bit)           |

LockはHRMのlock bitです。1でないといけません。SNIはspill number incrementであり、1であればスピル番号が変わったことを示しますが、そのように動作しているかどうかはチェックしていません。 Spill NumEvent NumはそれぞれHRMが受信したスピルナンバーとイベントナンバーです。

SCR word
|  SCR block (4-bit)   |                            Counter (28-bit)                           |

SCR BlockそのデータがどのSCRブロックに属しているのかを示します。SCRデータにはチャンネル番号を示すフィールドが存在しません。データはチャンネルの番号の低いほうから高いほうへ順番に並んでいます。

SCR block bits 入力ポート
0x8 Main in U
0x9 Main in D
0xA Mezzanine U
0xB Mezzanine D

HUL MH-TDC

HUL MH-TDCはHUL RMの機能にmulti-hit TDCを追加したファームウェアです。HUL RMと多くの機能が共通のため、異なる点のみ記述します。

Firmware固有名と現在の最新版

固有名 0x30cc
メジャーバージョン 0x03
マイナーバージョン 0x04

更新歴

バージョン リリース日 変更点
v1.0 2016.12.23 初期版
v1.1 2017.01.15 RVMのデータヘッダを0x9Cから0xF9へ変更。
v1.2 2017.01.27 Vivado更新 2016.2 => 2016.4。Block bufferがBuildIn FIFOだったのでBRAMにして深さを4096にした。EventBufferの深さを2048から4096にしてpgfullを4058にした。TDCブロックのchannel bufferを分散RAMからBRAMへ変更。TRMの中間バッファを分散RAMからBRAMへ変更。Prog Full threshold導入。それにあわせて、RVMの中間バッファ深さを128へ変更。
v1.4 2017.05.09 Clearに応答しない(BUSYが立ちっぱなしになる)問題を解決。
v1.5 - HRMを使っていて尚且つClearが入るとハングする問題を解決。(未リリース)
v1.6 - 一度でもmax multihit (16 hit/ch)を使い切ると、それいこうのイベントがずれる問題に対処。(未リリース)
v1.7 2017.08.22 FPGA内部のイベントシーケンスのバグを修正。
v1.8 2017.12.19 リセットシーケンスを統一。Header3の24ビット目にHRMが刺さっているかどうか(正確にはDIP2がONかどうか)を示すビットを挿入。高負荷な状況で稀にデータが壊れるバグを修正。ヘッダ2のワード数ビット幅を11-bitから12-bitへ変更。
v1.9 2018.02.02 >J0バスからやってくるイベントタグをラッチするタイミングが早すぎて、HRM側のイベント番号と1ずれるバグを解決。 Mezzanine HR-TDCで見られた、サーチウィンドウ外からデータが返ってくるバグの原因をMH-TDCも抱えているため、該当部分を改善した。
v2.x - 未公開
v3.4 2021.08.01 FMPとSDSを追加。Builder busの導入。Local busの構造変更。

モジュール動作概要
HUL MH-TDCではRMで動作未定義となっていた残りのmezzanine slot Dとメイン入力ポートに機能が割り当てられています。Mezzanine slotにはDCR v1 (v2)を実装することを想定しており、最大128ch分のTDCを取得することができます。また、mezzanine slot UにはDCRの代わりにHRMをマウントすることでHUL RMと同様J0 busマスタになることも可能です。この場合slot Uに割り当てられている32ch分のデータは削除されます。

MH-TDCは300 MHz 4相の多相クロック式のTDCを実装しており、1-bitの時間精度は0.83 nsです。Leadingとtrailingの両エッジを検出することができ、トリガーからさかのぼる事の出来る時間の長さは13.7 us、時間分解能は300 ps (σ)です。

mhtdc-fw

レジスタマップ

以下のテーブルはHUL MH-TDC専用のレジスタです。同名のモジュールやレジスタが他のfirmwareに存在しても同一のアドレスであるとは限りません。必ずこのマップ (もしくは配布したソフトウェアのRegisterMap.hh及びnamespace) にしたがって設定してください。 HUR RMの異なる部分は赤字で示してあります。

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: TRM (module ID = 0x00)
SelectTrigger 0x0000'0000 R/W 12 TRM内部のトリガーポートの選択を行うレジスタ。
DAQ Controller: DCT (module ID = 0x01)
DaqGate 0x1000'0000 R/W 1 DAQ gateのON/OFF。DAQ gateが0だとTRMはtriggerを出力できない。
EvbReset 0x1010'0000 W - このアドレスへ書き込み要求することでEVBのソフトリセットがアサートされ、Event builder内部のセルフイベントカウンタが0になる。
IO Manager: TDC (module ID = 0x02)
EnableBlock 0x2000'0000 R/W 4 どのブロック (入力ポート毎) を利用するか設定。ビットをhighにするとそのブロックのデータが取得できるようになります。入力ポートと対応するビットは
1bit目:Main in U
2bit目:Main in D
3bit目:Mezzanine U
4bit目:Mezzanine D
PtrOfs 0x2010'0000 R/W 11 内部制御変数。ユーザーは触らない。
WindowMax 0x2020'0000 R/W 11 Ring bufferからヒットを探す時間窓の上限値。1-bitが6.666... nsに相当。詳細は後述。
WindowMin 0x2030'0000 R/W 11 Ring bufferからヒットを探す時間窓の下限値。1-bitが6.666... nsに相当。詳細は後述。
IO Manager: IOM (module ID = 0x03)
NimOut1 0x3000'0000 R/W 4 NIMOUT1へ何を出力するかを設定する。
NimOut2 0x3010'0000 R/W 4 NIMOUT2へ何を出力するかを設定する。
NimOut3 0x3020'0000 R/W 4 NIMOUT3へ何を出力するかを設定する。
NimOut4 0x3030'0000 R/W 4 NIMOUT4へ何を出力するかを設定する。
ExtL1 0x3040'0000 R/W 3 extL1にどのNIMINを接続するか設定。
ExtL2 0x3050'0000 R/W 3 extL2にどのNIMINを接続するか設定。
ExtClr 0x3060'0000 R/W 3 Ext clearにどのNIMINを接続するか設定。
ExtBusy 0x3070'0000 R/W 3 Ext busy入力にどのNIMINを接続するか設定。
ExtRsv2 0x3080'0000 R/W 3 Ext rsv2入力にどのNIMINを接続するか設定。

各ブロックの機能

Trigger Manager (TRM)
機能およびレジスタはHUL RMと同様です。

Multi-Hit TDC (MH-TDC)
本ファームウェアの主機能です。本MH-TDCは4相クロックを使うことにより、擬似的に1.2 GHzを作り出しています。に示すmulti-hit TDCブロックには、TDC unit、ring buffer、channel bufferの3つのコンポーネントが存在します。TDC unitは擬似1.2 GHzで時間を測定し、ヒット検出を行います。TDC unitの時間分解能は300 ps (σ)、検出可能最小パルス幅はおよそ4 nsです。検出したヒット情報はring bufferに保存されます。ring bufferの長さは13.7 usで、ring bufferの書き込み・読み出しポインタがコースカウントに相当します。Ring bufferは150 MHzのクロックで駆動されているため、コースカウントは6.666...ns精度です。

L1 triggerを検出するとring bufferからの読み出しを開始します。この時、ヒットを探す範囲をWindowMaxレジスタおよびWindowMinレジスタによって設定可能です。これらのレジスタは1-bitがコースカウント精度の11-bitの整数値です。この範囲に入らないヒットはchannel bufferへ書き込まれません。Ring bufferからヒット情報を探している間busyが出力されます。

Channel bufferからblock bufferへデータをまとめる際に、1 ch/evenに許される最大ヒット数が設定されます。1 ch/eventに許されるヒットはTDC chの大きいほうから16ヒットまでです。それ以上のヒットがchannel bufferに記録されていた場合、16を超えるデータは破棄され、overflowビットが立ちます。

Multi-hit TDC仕様
TDC精度 0.833... ns
コースカウント精度 6.66... ns
Ring buffer長 13.8 us
時間分解能 300 ps (σ) *実測
最小パルス幅 ~4 ns
ダブルヒット分解能 ~7 ns
最大ヒット数/ch/event 16

I/O Manager (IOM)

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_ModuleBusy 0x0 Module busyです。Module busyは自身の内部busyのみを指します。J0 busのbusyやExtBusyは含まれません。
Reg_o_CrateBusy 0x1 CrateBusyです。CrateBusyはmodule busyに加えてJ0 busのbusyやExtBusyを含みます。J0 busマスタの場合に利用する信号になり、またHRMが Trigger Moduleへ返すbusyと同等です。
Reg_o_RML1 0x2 HRMが受信したL1 triggerを出力します。
Reg_o_RML2 0x3 HRMが受信したL2 triggerを出力します。
Reg_o_RMClr 0x4 HRMが受信したL2 triggerを出力します。
Reg_o_RMRsv1 0x5 HRMが受信したReserve 1を出力します。
Reg_o_RMSnInc 0x6 HRMがSpill Number Incrementを出力します。
Reg_o_DaqGate 0x7 DCTのDAQ gateを出力します。
Reg_o_DIP8 0x8 DIP SW2 8番のレベルを出力します。
Reg_o_clk1MHz 0x9 1 MHzのクロックを出力します。
Reg_o_clk100kHz 0xA 100 kHzのクロックを出力します。
Reg_o_clk10kHz 0xB 10 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
内部信号線へ割り当て可能なNIMINポート
Reg_i_nimin1 0x0 NIMIN1番を信号線へアサインします。
Reg_i_nimin2 0x1 NIMIN2番を信号線へアサインします。
Reg_i_nimin3 0x2 NIMIN3番を信号線へアサインします。
Reg_i_nimin4 0x3 NIMIN4番を信号線へアサインします。
Reg_i_default 0x7 このレジスタが設定された場合、指定のデフォルト値がそれぞれの内部信号線へ代入されます。

以下はIOMレジスタの初期値のテーブルです。

NIM出力ポート 初期レジスタ
NIMOUT1 Reg_o_ModuleBusy
NIMOUT2 reg_o_DaqGate
NIMOUT3 reg_o_clk1kHz
NIMOUT4 reg_o_DIP8
内部信号線 初期レジスタ デフォルト値
ExtL1 Reg_i_Nimin1 NIMIN1
ExtL2 Reg_i_default 0
ExtLClear Reg_i_default 0
ExtLBusy Reg_i_nimin3 NIMIN3
ExtLRsv2 Reg_i_nimin4 NIMIN4

HUL上のスイッチ・LEDの機能

DIP SW2の機能
HUL RMと同様です。

LED点灯の機能
HUL RMと同様です。

DAQの動作

データフローをに示します。HUL RMにMH-TDCが追加され、DIP SW2のmezzanine HRMがOFFであればTDCのみからデータを集め、mezzanine HRMがONであればTDCとRVM両方からデータを集めてイベントビルトします。ヘッダ2のNumber Of WordにはTDCとRVMの合計ワード数が入ります。

daq-mhtdc-fw

Module Busyとなるタイミング
HUL MH-TDCのmodule busyの定義は以下に列挙するbusy信号のORになります。普段はsequence busy分のbusy長となるはずです。現在self-busyに210 nsが設定されていますが、若干長めのため将来的に短くする可能性があります。HUL RMとself-busyの長さが異なるのは使っているシステムクロックの周波数が異なるためです。

BUSY種別 BUSY長 備考
Self busy 210 ns L1 triggerを検出した瞬間から固定長でアサート。
Sequence busy サーチ窓幅に依存 Ring bufferからヒット情報を探している間、すなわち`(WindowMax-WindowMin) x 6.66.. ns`分のbusyが出力されます。
Block full - ブロックバッファがfullになった段階でBUSYが出力されます。L1 triggerレートが後段の回路のデータ処理速度を上回るとアサートされます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。
SiTCP full - SiTCPのTCPバッファがFullになると出力されます。ネットワーク帯域に対してEvent Builderが送信しようとするデータ量が多いとアサートされます。

データ構造
Header word

Header1 (Magic word)
MSB                                                                                          LSB
|                                           0xFFFF30CC                                         |

Header2 (event size)
|       0xFF       |      0x00       |    "0000"    |         Number of word (12-bit)          |

Number of wordはデータボディに何ワード含まれるかを示します。ヘッダの3ワードは含みません。

Header3 (event number)
|       0xFF       | HRM exist | "000" | Tag (4-bit) |         Self counter (16-bit)           |

HRM existが1の場合HRMメザニンカードが取り付けられていることを示します。すなわち、データボディにRVMのデータワードが存在します。 TagはTRMから受信した4-bitのタグ情報です。下位3ビットがMTMが送信したイベントナンバーの下位3ビットに相当し、4ビット目がスピルナンバーの最下位ビットです。 Self counterはイベントが送信されるたびにインクリメントされるローカルイベント番号です。0から始まります。

Data body

RVM word
|  0xF9   | "00"  | Lock  | SNI  | Spill Num (8-bit) |            Event Num (12-bit)           |

LockはHRMのlock bitです。1でないといけません。SNIはspill number incrementであり、1であればスピル番号が変わったことを示しますが、そのように動作しているかどうかはチェックしていません。 Spill NumEvent NumはそれぞれHRMが受信したスピルナンバーとイベントナンバーです。

TDC word
|  Magic word (8-bit)  |  "0" + Ch (7-bit)  | "00" |            TDC (14-bit)                   |

Magic wordの定義は以下のようになります。

  • 0xCC Leading
  • 0xCD Trailing

Chには0から127までのチャンネル番号が入ります。チャンネルアサインについては2章を参照してください。 TDCはTDCデータです。

Mezzanine HR-TDC 及びHUL HR-TDC BASE

Mezzanine HR-TDC内部のファームウェアとそれを制御するためのファームウェアの説明です。Mezzanine HR-TDCはHUL MH-TDCでいうblock bufferまでの機能を別FPGAへ実装したファームウェアになり、HUL HR-TDC BASEはそれ以降のevent builderやtrigger managerといったDAQ全体を管理する機能を実装したファームウェアになります。よって、Mezzanine HR-TDCは複雑な動作はできません。Trigger(Common stop)に応答して測定データをHULへ転送するだけがその機能になります。一方で、その制御系はFPGAが2つあるため若干複雑です。また、Mezzanine HR-TDCはtapped-delay-lineのcalibration LUTを持っていたり、データ転送のためにDDR通信を行っていたりと他のファームウェアにない特徴を持っています。ここではこれらの機能と制御方法について説明します。

Mezzanine HR-TDC固有名と現在の最新版
以前はリーディングエッジのみ測定できるファームウェアと両エッジ測定できるファームウェアは区別されていましたが、新しいファームウェアでは1つに統合されました。測定するエッジの選択はレジスタで行います。

固有名 0x80cc
メジャーバージョン 0x05
マイナーバージョン 0x00

更新歴

バージョン リリース日 変更点
v2.5 2017.12.19 リーディング測定FWの初期版
v2.6 2018.02.02 サーチウィンドウ外からデータが返ってくるバグを解決。
v3.2 2017.12.19 リーディング・トレーリング測定FWの初期版
v3.3 2018.02.02 サーチウィンドウ外からデータが返ってくるバグを解決。
v4.5 2021.08.01 SEMとXADCの導入。Builder busの導入。測定エッジのレジスタによる選択を可能に変更。
XDC上にあった軽微な間違いを修正 (v4.3とは機能的に変わらない)。
このバージョンまでTDCサンプリングクロックとシステムクロックの周波数は520 MHzと130 MHz。
v5.0 2023.01.17 メザニンカードからのトリガー信号出力を実装した。
Local bus bridgeを修正した。Mezzanine FW v5.0はv3.7以前のHUL HRTDC BASEファームウェアと互換性がない。
TDCサンプリングクロックとシステムクロックを500 MHzと125 MHzへ変更。

モジュール動作概要
Mezzanine HR-TDCとHUL HR-TDC BASEを接続した状態のブロック図をに示します。制御系が他のファームウェアよりも複雑なため、多少詳しく描いています。HR-TDCのシステムはそれぞれのFPGAにBCTが存在し、mezzanine HR-TDC側はBASE側のBusBridgeを通じて2段階アクセスでレジスタを制御します。BsuBridgeを通じたMezzanine側の制御については専用のC++関数が用意されており、ソフトウェアのセクションでもう一度説明します。

時間測定のみを行うMezzanine HR-TDCと、イベントビルトやトリガー制御、および各IOの管理を行うBASE側に分かれます。トリガー情報の管理は他のモジュール同様にTrigger Manager (TRM)が行います。Mezzanine HR-TDCへはTRMが出力したlevel 1 triggerのみが送信されます。この信号がmezzanine HR-TDCにとってはcommon stop信号です。TDCとしての動作はHUL MH-TDCと同等です。時間精度だけがよりよくなったと思ってください。ヒットを記録するためのリングバッファ長は15.7 us、時間分解能は25 ps (σ) (common stopに対して)、20 ps (σ) (チャンネル間の差分)です。

DAQデータをmezzanineからBASEへ高速で転送するために、5線の信号線を使ってデータを送っています。制御ビットを含んで転送しているため5線の帯域を全て使えているわけではなく、1ワード (32 bit) 転送するのにかかる時間は8 ns (4 Gbps) です。BASE側のDDR receiverは電源投入後に一度初期化する必要があります。この方法についてもソフトウェアの節で説明します。TDC baseは送られてきたデータを見て、event builderに渡す準備をします。

blocks-hrtdc-fw

Mezzanine HR-TDCについての詳細説明

高分解能時間測定の原理
本ファームウェアはtapped-delay-line(TDL)方式という時間測定方法をとっています。TDLの概念をに示します。TDLはごく細かい遅延量を持つ素子を直列につないだ遅延ライン上を、入力信号がどこまで走ったかをフリップフロップで記録することにより、クロックエッジ間の時間情報の補間を行う技術です。の灰色の四角形は遅延素子を示し、各遅延素子の間の情報をD-FFアレイが毎クロックスナップショットを取っています。遅延素子を以後tapと呼ぶことにします。スナップショットを取るためのクロックは500 MHz (2.0 ns)のため、2.0 nsの間にパルスが到達可能な最大のtap番号が分かればtap当たりの遅延量dTが分かります。これは十分な数の統計があれば、tap番号のエンドポイントがそれに相当します。簡単には「2000 ps/最大tap番号」がtapあたりのdTであり、TDC 1-bit分の時間になります。ところが、FPGA HR-TDCではtapの遅延量はすべて異なるので、静的な校正ではなく、全てのtap番号を時間に変換する校正が必要になります。ここで、tap番号をfine count、fine countから時間に変換された値をestimatorと呼びます。

hrtdc-tdl

時間校正
Estimatorを生成するための手順をに示します。横軸をtap番号として、時間相関のない入力対するヒストグラムを生成します。各ビンの重さがdTの値に比例します。ここでヒストグラムの総エントリー数は固定値であり、ある値 (0x7ffff)に達するまでヒストグラムへのデータフィルを続けます。ヒストグラムが用意出来たら各ビンカウントを積分しestimatorを生成します。i番目のビンのエントリー数をwiとすると、N番目のestimatorは

En=wn/2+0n1(wi) E_{n} = w_{n}/2 + \sum^{n-1}_{0}(w_{i})

として計算されます。そのため、FPGA内部にはfine count ヒストグラムを生成するための機構とfine countからestimatorへ変換して出力する回路が必要になります。最も分かりやすい方法は検出器の信号を使ってfine count ヒストグラムを生成する方法です。(検出信号はランダムである必要があります。)ヒストグラム生成はDAQとは無関係であるため、入力信号は全て自動的にヒストグラムへフィルされていきます。しかし、この方法では0x7ffffまでイベント溜まるまで待たないといけなく、また、検出器が繋がっているチャンネルでしか利用できません。そのため、クロックを使ってヒストグラムを生成する方法を用意しています。FPGA内部で校正専用のクロックを全入力ラインに接続します。このクロックはTDLをサンプリングするクロックに対して毎エッジ少しずつ位相がずれていくように調整されています。原理的には1psずつ異なった場所に校正クロックのエッジを立てることが出来ます。校正クロックを使った方法では数十msでヒストグラムを生成することが出来ます。電源投入後のモジュールの初期化やRUNの最初に校正することを想定しています。

hrtdc-estimator

実装されている校正ブロックと動作
時間校正のシステムは2つのRAMによって実装されます。に示すようにfine countは2つのRAMへ同時に入力されます。片方のRAMはfine countからestimatorへ変換する仕事をします。生のestimatorは19-bit幅でそのままでは過剰なので、下位8-bitを捨てて11-bit幅にしてから出力します。対してもう一方のRAMではヒストグラムの生成を行っています。0x7ffffイベント溜まった時点でestimatorへ変換し、RAMのスワップ待ちの状態になります。RAMスワップは片方が準備できたら自動的に切り替えるか、手動で気切り替えるかを選ぶことが出来ます。これをつかさどっているのが、Controll::AutoSwReqSwitchです。Controll::AutoSwが1であれば自動切り替え、0であればReqSwitchへ書き込み動作をするとRAMが手動で切り替わります。自動切り替えはRUN中であっても検出器の信号を使ってRAMを常に更新したい場合に利用します。

また、estimatorへ変換せずにfine countをそのまま取り出したい場合もあると思います。その場合は、Controll::Throughを1にすることでfine countが直接現れます。

hrtdc-lut

HR-TDC system
Mezzanine HR-TDC内部のHR-TDC機能についてまとめます。本ファームウェアではTDLの長さは192 tapsですが、そのままだと遅延時間が細かすぎるため、3つのtapを1つにまとめて64の有効tapに変換しています。そのため、fine countの最大値は63となります。測定した結果では、2.0 nsでパルスが走る距離はおおよそ55 tapsです。出力されたfine countは125 MHzのクロック領域に渡され、estimatorへ変換されたのち、ring bufferへhit bitと一緒に書き込まれます。にあるようにestimator (11bit) + semi-coarse count (2bit) + coarse count (11bit)で24bitのデータ長になります。その後、mezzanine HR-TDCの中で一度部分的にイベントビルドされ、HUL側へ転送されます。簡単に時間に直すにはestimatorの最大値2048と500 MHzのクロックの値を使って、 時間 = TDC value/2048/ClkFreq (ClkFreq = 0.50 GHz (FW ver 5.0 以降) もしくは = 0.52 GHz (FW ver 4.5以前)) とすることで時間 (ns)に直ります。もっと正確に時間に直したい場合はTDC calibratorを使ってください。 Ring buffer以降の実装はMH-TDCと同一です。L1 trigger(common stop)を検出するとring bufferからの読み出しを開始します。この時、ヒットを探す範囲をWindowMaxレジスタおよびWindowMinレジスタによって設定可能です。これらのレジスタは1-bitがコースカウント精度の11-bitの整数値です。この範囲に入らないヒットはchannel bufferへ書き込まれません。Ring bufferからヒット情報を探している間busyが出力されます。MH-TDCとは使っているシステムクロックが異なるため、coarse count精度が異なります。

その後channel bufferからblock bufferへデータをまとめる際に、1ch/eventに許される最大ヒット数が設定されます。1ch/eventに許されるヒットはTDC chの大きいほうから16ヒットまでで、それ以上のヒットがchannel bufferに記録されていた場合、16を超えるデータは破棄され、overflowビットが立ちます。

トリガー出力
Version 5.0よりHR-TDCからトリガー信号を出力できるようになりました。 前述のhit bitを全てのチャンネルに対して論理和取り出力します。 トリガー出力を利用しない場合、TrigMaskレジスタによりチャンネル毎にマスクする事が出来ます。

High-resolution TDC 仕様
TDC精度 ~30 ps
コースカウント精度 8.0 ns
Ring buffer長 16.3 us
時間分解能 20 ps (σ) *実測
最小パルス幅 ~2 ns
ダブルヒット分解能 ~4 ns
最大ヒット数/ch/event 16

hrtdc-tdcblock

レジスタマップ

Mezzanine HR-TDCのレジスタについてまとめます。ここに記述しているレジスタはRegisterMap.hh内でnamespace HRTDC_MZNに属するものです。 Mezzanine HR-TDCへはBus Bridge Primary (BBP)を通じてバスブリッジしてアクセスするため、RBCPのアドレスで直接指定することは出来ません。 Version 5.0よりlocal bus bridgeを修正したことでアドレス範囲が12-bit幅から16-bit幅へ拡張されました。

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: DCT (module ID = 0x0)
TestMode 0x0000 R/W 1 HUL側のDDR receiverを初期化するためにDDR transmitterからテストパターンを出力するモード。電源投入時のモジュール初期化に必要で、配布しているC++ソフトウェアのddr_initialize内部で使用する。
ExtraPath 0x0010 R/W 1 このビットを立てると信号入力経路が基板上の入力ポートから校正クロックに切り替わる。前述のestimatorを校正クロックによって生成するために使用。
Gate 0x0020 R/W 1 DAQ gate。1だとcommon stopがHR-TDCへ入力される。
EnBlocks 0x0030 R/W 2 Leading/trailing測定ブロックを有効化する。1ビット目がleading block、2ビット目がtrailing block。デフォルトで0のため必ず設定する必要がある。
DAQ Controller: TDC (module ID = 0x01)
Control 0x1010 R/W 3 HR-TDCの動作を変えるためのレジスタ。以下の3つのビットが存在。
Through (0x1)
AutoSw (0x2)
StopDout (0x4)
Throughが1だとfine countはestimatorへ変換されずにそのまま出力される。AutoSwが1だと前述のestimator RAMが準備出来次第RAMのスワップを行う。StopDoutが1だとFPGA内部でcommon stopとの引き算を取らずに、stopのデータも1ワードとして転送する。
ReqSwitch 0x1020 W - `AutoSw`が0の場合、このレジスタへ書き込みを行おうとするとestimator RAMのスワップを行う。
Status 0x1030 R 1 1であれば次のEstimator RAMの準備が出来ていることを表す。
PtrOfs 0x1040 R/W 11 内部制御変数。ユーザーは触らない。
WindowMax 0x1050 R/W 11 Ring bufferからヒットを探す時間窓の上限値。1bitが8.0 nsに相当。詳細はMH-TDCを参照。
WindowMin 0x1060 R/W 11 Ring bufferからヒットを探す時間窓の下限値。1bitが8.0 nsに相当。詳細はMH-TDCを参照。
TrigMask 0x1070 R/W 32 各チャンネルのトリガー出力をマスクする。各ビットがチャンネルに対応しており、0にセットするとマスクされる。例:チャンネル0をマスクする場合、0xFFFF'FFFEをセットする。
DAQ Controller: SDS (module ID = 0xC)
SdsStatus 0xC000 R 8 SDSモジュールのステータスを取得します。
XadcDrpMode 0xC010 R/W 1 XADCのDRPモード選択をします。
  • 0x0: Read mode
  • 0x1: Write mode
XadcDrpAddr 0xC020 R/W 7 XADCのDRP addressを与えます。
XadcDrpDin 0xC030 R/W 16 XADCのDRPのデータ入力を与えます。
XadcDrpDout 0xC040 R 16 XADCのDRPのデータ出力を取得します。
XadcExecute 0xC050 W - XADCのDRPアクセスを実行します。
SemCorCount 0xC0A0 R 16 訂正可能なSEUをSEMが訂正した回数を取得します。
SemRstCorCount 0xC0B0 W - SemCorCountをリセットします。
SemErroAddr 0xC0C0 W 40 SEMのinject_addressポートに入力するアドレスを与えます。
SemErroStrobe 0xC0D0 W - SEMのinject_strobeポートにパルスを入力します。
DAQ Controller: BCT (module ID = 0xE)
Reset 0xE000 W - Bus Controllerからモジュールリセット信号をアサートし、SiTCPを除く全モジュールを初期化。
Version 0xE010 R 32 Firmwareの固有名とバージョンを読み出す。多バイト読み出しが必要。
Reconfig 0xE020 W - PROG_B_ONをLowにしてFPGAの再コンフィギュレーションを行う。一度通信が切れるので暫くしてから再接続。

Mezzanine上のスイッチ・LEDの機能

DIP SWの機能
基板上の4bit DIPスイッチに割り当てられている機能です。

スイッチ番号 機能 詳細
1 - 未使用
2 - 未使用
3 - 未使用
4 - 未使用

LED点灯の機能
Mezzanine HR-TDCにはユーザーが利用できるLEDはありません。赤いLEDはFPGAがコンフィグされていることを示すLEDです。

Module Busyとなるタイミング
Mezzanine HR-TDCのbusyの定義は以下に列挙するbusy信号のORになります。実際には更にHUL HR-TDC BASEのbusyもORしたものがシステムのbusyとなります。普段はsequence busy分のbusy長となるはずです。

BUSY種別 BUSY長 備考
Sequence busy サーチ窓幅に依存 Ring bufferからヒット情報を探している間、すなわち`(WindowMax-WindowMin) x 8.0 ns`分のBUSYが出力されます。
Block full - ブロックバッファがfullになった段階でBUSYが出力されます。L1 triggerレートが後段の回路のデータ処理速度を上回るとアサートされます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。

HUL HR-TDC BASEについての詳細説明

HUL HR-TDC BASEはDDR receiverとBctBusBridgeを除けばその機能は殆どMH-TDCと同じです。ですが、MH-TDCと違いHRMを実装することはできません。そのため、J0 bus masterになることはできません。

DDR receiverは電源投入後一度初期化する必要がある以外はユーザーが能動的にアクセスすることはありません。BctBusBridgeはmezzanine slot upとdownにそれぞれ独立で用意されています。BusBridgeはHUL側のBCTとメザニン側のBCTの橋渡しをします。HUL側のBCTからはBusBridgeはローカルモジュールの一種、メザニン側のBCTからは外部リンクのように見えます。メザニンへアクセスするためには2度のアクションを行う必要があります。1回目のアクションでHUL側のBCTはBusBridgePrimary (BBP)に対して、読み書きのコマンド値、メザニン側のlocal address、および書き込むべきレジスタ値(書き込みを行う予定の場合)をBBP内部へ格納します。2回目のアクションでBBP::Execを呼び出すと、バスブリッジを実行し通信を行います。メザニン側のBCTを書き込みで駆動するか、読み出しで駆動するかは、1回目のアクションで指定したコマンド値で決まります。BBPは通信プロセスが正しく終わるまでHUL側のBCTへ応答しません。そのため、例えばmezzanine HR-TDCが刺さっていないのにBBP::Execを呼ぶとHUL側のBCTがデッドロックします。この場合BCT::Resetを呼ぶことが出来なくなるのでSiTCP Resetで対応する必要があります。BusBridge制御のためのC++関数はBctBusBridgeFunc.ccにまとめられています。詳細は6章で述べます。

HR-TDC BASE固有名と現在の最新版

固有名 0x80eb
メジャーバージョン 0x04
マイナーバージョン 0x01

更新歴

バージョン リリース日 変更点
v1.5 2017.12.19 初期バージョン
v1.6 - 未公開
v1.7 2018.02.02 J0バスからやってくるイベントタグをラッチするタイミングが早すぎて、HRM側のイベント番号と1ずれるバグを解決。 BCT::Resetを呼ぶとBCTがハングするバグを解決。
v3.7 2021.08.01 SDS, FMPの追加。Builder busの導入。BCTの構造変更。
v4.0 2023.01.17 Mezzanine HR-TDC v5.0.対応版。Mezzanine HR-TDC v4.5以前のバージョンはサポートしていない。
v4.1 2023.02.24 v4.0が正しく動作しないことがあるバグを発見。v4.1はその対策版。

レジスタマップ

これはHUL HR-TDC BASE側のレジスタマップであり、RegisterMap.hh内部でnamespace HRTDC_BASEに属します。Mezzanine側と名前が被るものもあるので、必ずnamespaceで指定してください。IOMにおいてHRMをサポートしなくなったことによっていくつかのレジスタが存在しません。

加えて本ファームウェア用のRegisterMap.hhには先頭にkEnSlotupkEnSlotDownというグローバル変数が記述されています。これはどのスロットにmezzanine HR-TDCが刺さっているかを示すフラグです。Mezzanine HR-TDCが刺さっていないスロットはfalseにしてください。各実験の本番用ソフトに移植する際には無くても良い変数です。

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: TRM (module ID = 0x00)
SelectTrigger 0x0000'0000 R/W 12 TRM内部のトリガーポートの選択を行うレジスタ。
DAQ Controller: DCT (module ID = 0x01)
DaqGate 0x1000'0000 R/W 1 DAQ gateのON/OFF。DAQ gateが0だとTRMはtriggerを出力できない。
EvbReset 0x1010'0000 W - このアドレスへ書き込み要求することでEVBのソフトリセットがアサートされ、Event builder内部のセルフイベントカウンタが0になる。
InitDDR 0x1020'0000 W - DDR receiverへ向けて初期化要求を行う。
CtrlReg 0x1030'0000 R/W 4 DDR receiverを制御するためのレジスタ。詳細は後述。
Status 0x1040'0000 R 4 DDR receiverのステータスレジスタ。詳細は後述。
IO Manager: IOM (module ID = 0x02)
NimOut1 0x2000'0000 R/W 4 NIMOUT1へ何を出力するかを設定する。
NimOut2 0x2010'0000 R/W 4 NIMOUT2へ何を出力するかを設定する。
NimOut3 0x2020'0000 R/W 4 NIMOUT3へ何を出力するかを設定する。
NimOut4 0x2030'0000 R/W 4 NIMOUT4へ何を出力するかを設定する。
ExtL1 0x2040'0000 R/W 3 extL1にどのNIMINを接続するか設定。
ExtL2 0x2050'0000 R/W 3 extL2にどのNIMINを接続するか設定。
ExtClr 0x2060'0000 R/W 3 Ext clearにどのNIMINを接続するか設定。
ExtBusy 0x2070'0000 R/W 3 Ext busy入力にどのNIMINを接続するか設定。
cntRst 0x2090'0000 R/W 3 Mezzanine HR-TDC内部のcoarse countをリセットするハードリセット信号。複数台のHR-TDCを同期したい場合に使用する。この線にどのNIMINを接続するか設定。
Bus Bridge Primary: BBP (module ID = 0x3, 0x4)
Txd 0x3000'0000 W 32 Slot-UのセカンダリFPGA (mezzanine card上のFPGA) に対してlocal bus bridgeを介してへ書き込むデータ。
Rxd 0x3010'0000 R 32 Slot-UのセカンダリFPGAからlocal bus bridgeを介して読み出したデータ。
Exec 0x3100'0000 W - Bus bridge primaryを駆動しslot-UのセカンダリFPGAと通信を行うためのスタート信号をアサートする。
Txd 0x4000'0000 W 32 Slot-DのセカンダリFPGA (mezzanine card上のFPGA) に対してlocal bus bridgeを介してへ書き込むデータ。
Rxd 0x4010'0000 R 32 Slot-DのセカンダリFPGAからlocal bus bridgeを介して読み出したデータ。
Exec 0x4100'0000 W - Bus bridge primaryを駆動しslot-DのセカンダリFPGAと通信を行うためのスタート信号をアサートする。

Trigger Manager (TRM)
HUL HR-TDC BASEはHRMをマウントすることが出来ないため、TRMのRMに関するレジスタは機能しません。

レジスタラベル レジスタ値 備考
RegL1Ext 0x1 NIMINからL1 triggerを選択。
RegL1J0 0x2 J0 busからのL1 triggerを選択。
RegL2Ext 0x8 NIMINからのL2 triggerを選択。
RegL2J0 0x10 J0 busからのL2 triggerを選択。
RegClrExt 0x40 NIMINからのClearを選択。
RegClrJ0 0x80 J0 busからのClearを選択。
RegEnL2 0x200 0: L2=L1 trigger、1: L2=L2入力
RegEnJ0 0x400 Tag情報にJ0 busの物を採用する。また、このbitが1だとJ0 busへ自身のmodule busyを流す。

DAQ controller (DCT)

DCT内部のCtrlRegStatusが示すビットの詳細を述べます。

レジスタラベル Bit番号 備考
CTRLレジスタの内訳
RegTestModeU 1st bit (0x1) このビットを立てると、DDR receiver (slot-U)を初期化するために、テストパターンを受信するモードへ切り替える。
RegTestModeD 2nd bit (0x2) このビットを立てると、DDR receiver (slot-D)を初期化するために、テストパターンを受信するモードへ切り替える。
EnableU 3rd bit (0x4) このビットを立てるとDDR receiver (slot-U)が利用可能になる。
EnableD 4th bit (0x8) このビットを立てるとDDR receiver (slot-D)が利用可能になる。
FRstU 5th bit (0x10) このビットを立てるとSlot-UのFPGAに倒してフォースリセット信号をアサートする。v3.7以前のファームウェアではMIFブロックに実装されていた機能。
FRstD 6th bit (0x20) このビットを立てるとSlot-DのFPGAに倒してフォースリセット信号をアサートする。v3.7以前のファームウェアではMIFブロックに実装されていた機能。
Statusレジスタの内訳
BitAlignedU 1st bit (0x1) DDR receiver (slot-U)のbit slipが終了し、データ読み出しが可能になった事を示す。
BitAlignedD 2nd bit (0x2) DDR receiver (slot-D)のbit slipが終了し、データ読み出しが可能になった事を示す。
BitErrorU 3rd bit (0x4) DDR receiver (slot-U)のbit slipを一定回数施行したが、正しい結果が返ってこなかった事を示す。初期化失敗。
BitErrorD 4th bit (0x8) DDR receiver (slot-D)のbit slipを一定回数施行したが、正しい結果が返ってこなかった事を示す。初期化失敗。

I/O Manager (IOM)

HRMをサポートしないため複数のレジスタが機能しません。

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_ModuleBusy 0x0 Module busyです。Module busyは自身の内部busyのみを指します。J0 busのbusyやExtBusyは含まれません。
Reg_o_DaqGate 0x7 DCTのDAQ gateを出力します。
Reg_o_DIP8 0x8 DIP SW2 8番のレベルを出力します。
Reg_o_clk1MHz 0x9 1 MHzのクロックを出力します。
Reg_o_clk100kHz 0xA 100 kHzのクロックを出力します。
Reg_o_clk10kHz 0xB 10 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
Reg_o_TrigOutU 0xD Slot-Uのmezzanine HR-TDCから出力されるトリガー出力をアサインします。
Reg_o_TrigOutD 0xE Slot-Dのmezzanine HR-TDCから出力されるトリガー出力をアサインします。
Reg_o_TrigOutUD 0xF Slot-U/D両方のmezzanine HR-TDCから出力されるトリガー出力の論理和をアサインします。
内部信号線へ割り当て可能なNIMINポート
Reg_i_nimin1 0x0 NIMIN1番を信号線へアサインします。
Reg_i_nimin2 0x1 NIMIN2番を信号線へアサインします。
Reg_i_nimin3 0x2 NIMIN3番を信号線へアサインします。
Reg_i_nimin4 0x3 NIMIN4番を信号線へアサインします。
Reg_i_default 0x7 このレジスタが設定された場合、指定のデフォルト値がそれぞれの内部信号線へ代入されます。

IOMの初期レジスタです。

NIM出力ポート 初期レジスタ
NIMOUT1 Reg_o_ModuleBusy
NIMOUT2 reg_o_DaqGate
NIMOUT3 reg_o_clk1kHz
NIMOUT4 reg_o_DIP8
内部信号線 初期レジスタ デフォルト値
ExtL1 Reg_i_Nimin1 NIMIN1
ExtL2 Reg_i_default 0
ExtLClear Reg_i_default 0
ExtLBusy Reg_i_nimin3 NIMIN3
cntRst Reg_i_default 0

DIP SW2の機能
DIP SW2に割り当てられている機能を列挙します。

スイッチ番号 機能 詳細
1 SiTCP force default ONでSiTCPのデフォルトモードで起動します。電源投入前に設定している必要があります。
2 Not in use 未使用
3 Force BUSY Crate busyとmodule busyを強制的にhighにします。接続チェックなどに使ってください。
4 Bus BUSY ONでCrate BusyにJ0 bus busyを含め、OFFで含めません。
5 LED ONでLED4番を光らせます。
6 Not in Use
7 Not in Use
8 Level IOMのDIP8から出力されるレベルです。
LED番号 備考
LED1 点灯中はTCP接続が張られています。
LED2 点灯中はmodule busyがhighです。
LED3 DAQ gateがONであると点灯。
LED4 点灯中はDIP SW2のLEDがONです。

DAQの動作

データフローをに示します。Mezzanine HR-TDCとBASEが2つのFPGAへ分かれていますが、見かけの動作はHUL MH-TDCと変わりません。各mezzanineではblock bufferに相当する部分までの部分的なイベントビルドが行われデータがBASEへ転送されてきます。BASE側では受け取ったデータをまとめてイベントビルドします。

daq-hrtdc-fw

Module Busyとなるタイミング
システム全体のBUSY条件をのべます。Module busyはこれらのORです。

BUSY種別 BUSY長 備考
Self busy 210 ns L1 triggerを検出した瞬間から固定長でアサート。
Mezzanine busy Mezzanineの状態に依存 Mezzanine HR-TDCが出力しているBUSY。通常はサーチ窓幅のbusyが返ってきます。
Block full - TDC BaseのブロックバッファがFullになった段階でbusyが出力されます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。
SiTCP full - SiTCPのTCPバッファがFullになると出力されます。ネットワーク帯域に対してEvent Builderが送信しようとするデータ量が多いとアサートされます。

データ構造
ヘッダワード

Header1 (Magic word)
MSB                                                                                          LSB
|                                           0xFFFF80EB                                         |

Header2 (event size)
|   0xFF00   |   OvrFlow   |    "000"    |            Number of word (12-bit)                  |

Number of wordはデータボディに含まれるワード数を示します。Number of WordはSub-header分の2ワード分を含みます。なので最低値が2です。OverFlowはHUL全体で1chでもover flowチャンネルがあると立ちます。

Header3 (event number)
|   0xFF   | "0000" |  Tag (4-bit)  |                 Self counter (16-bit)                    |

TagはTRMから出力される4bitのTag情報です。下位3bitがRM event Numberの下位3ビット、4ビット目がRM spill numberの最下位ビットとなります。Self counterはイベント転送を行うたびにインクリメントされるlocal event numberで、0オリジンです。

Sub-headers
|   0xFA00  | "0" |  OverFlow  |  StopDuout  |  Through  |          # of word (12-bit)         |
|   0xFB00  | "0" |  OverFlow  |  StopDuout  |  Through  |          # of word (12-bit)         |

それぞれmezzanine HR-TDCのヘッダです。0xFA000xFB00がそれぞれslot-Uと-Dに対応します。OverFlowはそれぞれのメザニン中でのover flowの存在を示しています。Stop doutThroughはそれぞれHRTDC_MZN::TDC::ControllにおけるStopDoutThroughの状態を示します。Number of wordは各メザニンのワード数を示します。

Data body

|  Magic word (3-bit)  |  Ch (5-bit)  |                     TDC (24-bit)                       |

Magic wordは以下のように定められています。

  • 6 Leading
  • 5 Trailing
  • 4 Common stop

となります。Chは5 bitしかない事が示すように31chまでしか数えることが出来ません。サブヘッダA・Bに属するデータであるかを見てデコードして、サブヘッダBに属するのであれば32ch足してください。TDCはHR-TDCの節で述べたようにestimator (11bit) + semi-coarse count (2bit) + coarse count (11 bit)で合計24 bitです。ThroughがONの場合fine countはestimatorの位置に現れます。

Three-dimensional matrix trigger

このファームウェアのバージョン表記は他のFWと異なっており、メジャーバージョンが1ですがFMPやSDSは搭載されています。

固有名 0xe033
メジャーバージョン 0x01
マイナーバージョン 0x01

更新歴

バージョン リリース日 変更点
v1.1 2020.12.02 実験で利用した最終版

動作概要
このファームウェアはJ-PARC E03実験とE42実験の際に用いられたマトリックスコインシデンストリガーです。似たような機能を持つマトリックストリガー回路を作成したい場合の例題として利用してください。本ファームウェアにはデータ収集機能はありません。このFWでは3種類のホドスコープの三次元相関からトリガーを生成します。にブロック図を示します。この実験ではBH2、TOF、SCHという3種類のタイミングホドスコープ間のマトリックス相関を用います。丸カッコ内の数字はチャンネル番号を表しており、合計14336パターン (8x28x64) の組み合わせが発生します。入力は二重FFで同期されます。クロック速度は350 MHzです。後述のDWGやマトリックスパターンのブロックも同様のクロックで駆動されています。BH2がNIM-INへも繋がれているのはテストを簡便に行うためです。このファームウェアはメザニンスロットがSCHの入力を受けるためDCR v1/v2が必須です。

同期された入力信号はDelay Width Generator (DWG) で幅と遅延時間の調整がされます。各DWGはRBCPを通じて調整が可能です。350 MHz (2.857... ns) のクロック精度で32段階の調整が可能です。詳しくはソフトウェアの項で述べます。DWGではパルス出力中にもう一度パルス入力があった場合2つのパルスを繋げます。麻痺型モデルで表されるデッドタイムの振る舞いと同様です。

MTX3DとMTX2Dはそれぞれ三次元マトリックスコインシデンスと二次元マトリックスコインシデンスのブロックです。このFWでは1つ三次元トリガーと2つの二次元トリガーが実装されており、それぞれマトリックスパターンを設定可能です。RBCPを用いて全てのマトリックスエレメント1つ1つのOn/Offの切り替えが可能です。どのように実現しているかは後述します。

各マトリックストリガーはIOMを通じてNIMOUTから出力可能です。このFWでは実験の要求から二次元マトリックスの出力を三次元マトリックスの結果でVETOする経路が用意されています。この実験では三次元トリガーがビームVETOの役割を果たしていたためタイミングが良く分かっており、二次元トリガーに対しては固定長ディレイでVETO位置を調整しています。このあたりは実験条件に合わせて変更してください。

mtx3d-fw

マトリックスパターンの設定方法

14336パターンのスイッチをアドレスで解決しようと思うととてつもなく大きなエンコーダが必要になり、一般的にFPGAで実現するのは非現実的です。ここで3次元のレジスタを(28x64)x8と分解すると、8-bit幅・1792長のレジスタと捉えることが出来ます。すなわち、8-bit幅で長さが1792のシフトレジスタを用意することで、全てのレジスタビットの設定が可能となります。二次元の場合1-bit幅で長さが1792のシフトレジスタを用意します。RBCP (BCT) は同一のアドレスに1792回書き込むだけで設定が実現でき、極めてリソース効率が良いです。レジスタ設定はシステムクロックに対して低速なクロックで行っても良いため、このFWでは10 MHzのクロックでシフトレジスタを駆動しています。

DWGの構造

DWGは遅延と幅の生成をシフトレジスタへのビットパターンのプリセットによって実現しています。例えば先頭から00011111000...というビットパターンを入力があったタイミングでシフトレジスタへセットしたとします。そうするとこのパターンは遅延量が3でパルス幅が5の波形を与えます。遅延量と幅の情報からビットパターンへの変換はソフトで行う事にしています。最大幅と遅延量がそれぞれ32のため、DWGの取るレジスタ幅は64-bitです。

レジスタマップ

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: MTX2D-1 (module ID = 0x00)
TofDWG 0x0000'0000 R/W 64 Tof (1-24) 入力のDWGレジスタを設定します。
TofExtDWG 0x0010'0000 R/W 64 Tof (25-28) 入力のDWGレジスタを設定します。
SchDWG 0x0020'0000 R/W 64 SCH入力のDWGレジスタを設定します。
TrigDWG 0x0030'0000 R/W 64 二次元トリガー出力のDWGを設定します。
EnableMtx 0x0040'0000 W 1 二次元マトリックスパターンを設定するアドレスです。シフトレジスタの最下位にレジスタを書きます。
ExecSR 0x0100'0000 W - 二次元マトリックスパターンを設定するシフトレジスタを1つシフトさせます。
Trigger Manager: MTX2D-2 (module ID = 0x01)
各レジスタはMTX2D-1と同様です
Trigger Manager: MTX3D (module ID = 0x02)
TofDWG 0x2000'0000 R/W 64 Tof (1-24) 入力のDWGレジスタを設定します。
TofExtDWG 0x2010'0000 R/W 64 Tof (25-28) 入力のDWGレジスタを設定します。
SchDWG 0x2020'0000 R/W 64 SCH入力のDWGレジスタを設定します。
Bh2DWG 0x2030'0000 R/W 64 SCH入力のDWGレジスタを設定します。
TrigDWG 0x2040'0000 R/W 64 三次元トリガー出力のDWGを設定します。
EnableMtx 0x2050'0000 W 8 三次元マトリックスパターンを設定するアドレスです。シフトレジスタの最下位にレジスタを書きます。
ExecSR 0x2100'0000 W - 三次元マトリックスパターンを設定するシフトレジスタを1つシフトさせます。
Trigger Manager: IOM (module ID = 0x03)
Nimout1 0x3000'0000 R/W 4 Nimout1ポートへの出力を設定します。
Nimout2 0x3010'0000 R/W 4 Nimout2ポートへの出力を設定します。
Nimout3 0x3020'0000 R/W 4 Nimout3ポートへの出力を設定します。
Nimout4 0x3030'0000 R/W 4 Nimout4ポートへの出力を設定します。

I/O Manager (IOM)

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_Trig3D 0x0 MTX3Dトリガーを出力します。
Reg_o_Trig2DVeto1 0x1 MTX3DでVETOされた後のMTX2D-1トリガーを出力します。
Reg_o_Trig2DVeto2 0x2 MTX3DでVETOされた後のMTX2D-2トリガーを出力します。
Reg_o_Trig2D1 0x3 MTX2D-1トリガーを出力します。
Reg_o_Trig2D2 0x4 MTX2D-2トリガーを出力します。
Reg_o_TofOR 0x5 TofORを出力します。
Reg_o_SchOR 0x6 SchORを出力します。
Reg_o_Bh2OR 0x7 Bh2ORを出力します。

Mass trigger (TOF based trigger)

このファームウェアは2023年現在更新がストップしています。Mezzanine HR-TDC v5.0や最新のソフトウェアとは互換性がありません。以前のバージョンの物を引き続き利用してください。

固有名 0x20d1
メジャーバージョン 0x03
マイナーバージョン 0x00

更新歴

バージョン リリース日 変更点
v3.0 2020.12.02 実験で利用した最終版

Mass trigger (MsT) はJ-PARC K1.8での通称であり、機能的にはTOFベースのトリガー生成回路です。ダイポール磁気スペクトロメータを通過した粒子の軌道は大雑把に粒子の運動量と相関があります。2つのホドスコープの二次元マトリックス相関から運動量範囲を制限し、各マトリックスエレメントに対してTOFの分布を取ると粒子の質量ごとにTOFピークが分離します(低い運動量であれば)。Mass triggerはmezzanine HR-TDCとHULのメイン入力を用いて、二次元マトリックスとTOF情報によるトリガー生成を行うためのファームウェアです。HR-TDCの情報を得るためにはcommon stop入力が必要であるため、mass triggerはlevel2 decisionを行い、level2 triggerかもしくはfast clear信号を生成することが仕事です。

ブロック図をに示します。MsTはHRMとHR-TDCのメザニンカードを必要としています。それぞれ、slot-Uとslot-Dへマウントしてください。Main INへ入力された信号は低速なTDCでデジタイズされヒットレジスタ情報を与えます。そのため、このファームウェアにおけるTOFは厳密には検出器間の時間差でなく、common stopとの時間差です。Mass triggerを利用するためにはlevel1 triggerが非同期回路で生成されている必要があります。この仕様はK1.8ビームラインの都合に合わせてあるため、真のTOFを計算させたい場合ファームウェアの改修が必要になります。

SCH (64ch)とTOF (32ch) 間の2048パターンに対してTOF windowのチェックを行います。この時、HR-TDCから返ってきたマルチヒットデータ全てに対して判定を行うため、同一チャンネルに対して複数回の判定が行われることがあります。1つでもアクセプト範囲にTOF値があればトリガーが発行されます。1つのアクセプト範囲にデータがない場合クリア信号が出力されます。アクセプト窓の設定はSiTCP経由で行います。MsTでトリガー判定を行いたいのはlevel1 triggerが物理トリガーの場合だけです。キャリブレーショントリガーの場合は判定無しでlevel2 triggerを発生させなければいけません。判定すべきlevel1 triggerかどうかを知らせるために、このファームウェアではpiK flagという信号をlevel1 triggerに続いて入力することになっています。Flag入力が無ければ判定を行わず、必ずlevel2 triggerが発行されます。

本ファームウェアにはデータ収集機能が存在します。HR-TDCとLR-TDCによって得られた時間情報と、MsTの判定結果がデータとして返ってきます。本ファームウェアはトリガー生成回路ですが、データ収集のためには外部からトリガー入力が必要です。

mst-fw

タイミングチャート
K1.8ビームラインでmass triggerを導入する目的は、主にVMEモジュール用にfast clearを生成し不必要なバスアクセス時間を減らす事です。K1.8ビームラインではchained-block-transfer (CBLT) でVMEバスアクセスを行っていますが、おおよそ100 usのバスアクセス時間がかかります。VMEモジュール内のmulti-event bufferを活用して、バスアクセス時間をlevel1 triggerに対するbusyに含めない工夫はしていますが、潜在的なbusyであるためlevel1 triggerのレートが7 kHzあたりから急激にDAQ効率が悪くなります。そのような実験ではmass triggerを導入してlevel2判定を加えてバスアクセスの回数を減らします。

に想定タイミングチャートを示します。Mass triggerはHR-TDCとLR-TDCにcommon stop入力が入った時点から動作を開始します。HR-TDCからデータの転送が終わると判定を開始します。Mass triggerはmulit-hitを全て処理するため、ここまでの時間は可変です。Level1から固定時間後に判定結果を出力するためにMST::TimerPresetで出力までの時間を設定します。今のファームウェアバージョンでは500程度の大きな値を設定することを推奨しています。MST::TimerPresetは判定プロセスよりも優先度が高いため、指定時間後に判定が終わっていなかった場合後述のno decision flagを立てたうえで強制的にlevel2 triggerを出力します。No decision flagが頻繁に立つ場合MST::TimerPresetの値が小さすぎます。

mst-timing

判定フロー
Level2 trigger判定のフロー図をに示します。図の下側に書かれているリストは各判定状態におけるフラグ(および内部信号)の状況を示しています。判定動作はlevel1 trigger受信で開始します。TDCブロックから情報を集め判定回路が各チャンネル独立に動作します。MST::TimerPresetに指定した時間がたった後、piK flagを受信しているか、および判定プロセスがすべて終了しているかのチェックを行います。どちらかを満たしていない場合、no decision flagを立ててlevel2 triggerを出力します。次にHR-TDCから取得したTDC値がアクセプト範囲にあるかどうかのチェックを行います。1つでも存在すればmass trigger acceptととなり、level2 triggerが出力されます。1つもない場合clear判定となり、敗者復活判定へ続きます。Clear判定を下されたイベントはDAQで取得されないため、クリアしているイベントをサンプル検査するためにMST::ClearPresetに指定した値に1度、敗者復活アクセプトを出します。敗者復活判定が下された場合consolation acceptのフラグが立ち、level2 triggerが出力されます。敗者復活の条件を満たさない場合fast clearが出力されます。

mst-chart

TOFのアクセプト範囲の設定
Mass triggerには2種類のTDC範囲設定を行うレジスタが存在します。LRTDC::WinMaxLRTDC::WinMin、およびmezzanine HR-TDCのウィンドウレジスタはcommon stop入力に対してヒットサーチを行う範囲を設定します。これは通常のTDCファームウェアと同様です。MST::WixMaxMST::WinMinはlevel2判定でアクセプトとなる範囲を与えます。Mass triggerでは32 chのHR-TDC入力と64 chのLR-TDC入力間の二次元マトリックスに対して、行列要素毎にこのレンジを設定することが出来ます。マトリックスコインシデンストリガーの時と同様に24-bit幅で長さが2048のシフトレジスタを採用しています。MST::WixMaxMST::WinMinの両方を0に設定すると、その行列要素に対しては判定を行いません。

レジスタマップ

レジスタ名 アドレス 読み書き ビット幅 備考
Trigger Manager: TRM (module ID = 0x00)
SelectTrigger 0x0000'0000 R/W 12 TRM内部のトリガーポートの選択を行うレジスタ。
DAQ Controller: DCT (module ID = 0x01)
DaqGate 0x1000'0000 W - DAQ gateのON/OFF。DAQ gateが0だとTRMはtriggerを出力できない。
EvbReset 0x1010'0000 R/W 1 このアドレスへ書き込み要求することでEVBのソフトリセットがアサートされ、Event builder内部のセルフイベントカウンタが0になる。
InitDDR 0x1020'0000 W - DDR receiverへ向けて初期化要求を行う。
CtrlReg 0x1030'0000 R/W 4 DDR receiverを制御するためのレジスタ。
Status 0x1040'0000 R 4 DDR receiverのステータスレジスタ。
IO Manager: IOM (module ID = 0x02)
NimOut1 0x2000'0000 R/W 5 NIMOUT1へ何を出力するかを設定する。
NimOut2 0x2010'0000 R/W 5 NIMOUT2へ何を出力するかを設定する。
NimOut3 0x2020'0000 R/W 5 NIMOUT3へ何を出力するかを設定する。
NimOut4 0x2030'0000 R/W 5 NIMOUT4へ何を出力するかを設定する。
ExtL1 0x2040'0000 R/W 3 extL1にどのNIMINを接続するか設定。
ExtL2 0x2050'0000 R/W 3 extL2にどのNIMINを接続するか設定。
ExtClr 0x2060'0000 R/W 3 Ext clearにどのNIMINを接続するか設定。
ExtBusy 0x2070'0000 R/W 3 Ext busy入力にどのNIMINを接続するか設定。
cntRst 0x2090'0000 R/W 3 Mezzanine HR-TDC内部のcoarse countをリセットするハードリセット信号。複数台のHR-TDCを同期したい場合に使用する。この線にどのNIMINを接続するか設定。
PiKTrig 0x20A0'0000 R/W 3 Mass triggerに対する物理トリガーフラグ入力。Level1 triggerに続いて入力があるとlevel2判定を行う。
IO Manager: MIF-Down
Connect 0x3000'0000 R/W - MIF-Downからmezzanine HR-TDCのBCTへ向けて通信プロセスを開始する。アクセスする際のモードが書き込みなのか読み出しなのかで、メザニンのBCTへのアクセス方法が切り替わる仕様となっている。
Reg 0x3010'0000 R/W 20 MIF-Downにmezzanine HR-TDC用のlocal addressと書き込み用レジスタ値をMIFに一時的に保存する。
  • [19:8]: Local address
  • [7:0]: Register valus
ForceReset 0x3100'0000 W - MIF-Downのmezzanine HR-TDCへ強制リセット信号をアサート。DAQやBCTがハングした場合に使用する。
Low-resolution TDC: LRTDC
PtrOfs 0x4010'0000 R/W 11 内部制御変数。ユーザーは触らない。
WindowMax 0x4020'0000 R/W 11 Ring bufferからヒットを探す時間窓の上限値。1-bitが6.666... nsに相当。
WindowMin 0x4030'0000 R/W 11 Ring bufferからヒットを探す時間窓の下限値。1-bitが6.666... nsに相当。
Mass trigger: MST
ClearPreset 0x5000'0000 R/W 7 このレジスタに書かれた値に1度、敗者復活アクセプトが出力される。0に設定すると敗者復活判定を行わない。
TimerPreset 0x5010'0000 R/W 9 Level1 triggerを受信してからlevel2 trigger/clearを出力するまでの遅延時間。
WinMax 0x5020'0000 W 24 アクセプトするTOF範囲の上限値を与えます。シフトレジスタの最下位にレジスタを書きます。
WinMin 0x5030'0000 W 24 アクセプトするTOF範囲の下限値を与えます。シフトレジスタの最下位にレジスタを書きます。
Exec 0x5040'0000 W - シフトレジスタを1つシフトさせます。
Bypass 0x5050'0000 R/W 1 このレジスタが1になると判定回路をバイパスしてlevel2 triggerを出力するようになります。実験中に一時的にmass triggerをバイパスしたい場合に利用します。

I/O Manager (IOM)

レジスタラベル レジスタ値 備考
NIMOUTへ出力可能な内部信号
Reg_o_ModuleBusy 0x0 Module busyです。Module busyは自身の内部busyのみを指します。J0 busのbusyやExtBusyは含まれません。
Reg_o_CrateBusy 0x1 CrateBusyです。CrateBusyはmodule busyに加えてJ0 busのbusyやExtBusyを含みます。J0 busマスタの場合に利用する信号になり、またHRMが Trigger Moduleへ返すbusyと同等です。
Reg_o_RML1 0x2 HRMが受信したL1 triggerを出力します。
Reg_o_RML2 0x3 HRMが受信したL2 triggerを出力します。
Reg_o_RMClr 0x4 HRMが受信したL2 triggerを出力します。
Reg_o_RMRsv1 0x5 HRMが受信したReserve 1を出力します。
Reg_o_RMSnInc 0x6 HRMがSpill Number Incrementを出力します。
Reg_o_DaqGate 0x7 DCTのDAQ gateを出力します。
Reg_o_DIP8 0x8 DIP SW2 8番のレベルを出力します。
Reg_o_clk1MHz 0x9 1 MHzのクロックを出力します。
Reg_o_clk100kHz 0xA 100 kHzのクロックを出力します。
Reg_o_clk10kHz 0xB 10 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
Reg_o_clk1kHz 0xC 1 kHzのクロックを出力します。
Reg_o_Accept 0xD Accept flagを出力します。
Reg_o_Clear 0xE Clear flagを出力します。
Reg_o_ConsolationAccept 0xF Consolation accept flagを出力します。
Reg_o_FinalClear 0x10 Final clear flagを出力します。
Reg_o_Level2 0x11 Level2 flagを出力します。
Reg_o_FastClear 0x12 Fast clear flagを出力します。
Reg_o_NoDecision 0x13 No decision flagを出力します。
内部信号線へ割り当て可能なNIMINポート
Reg_i_nimin1 0x0 NIMIN1番を信号線へアサインします。
Reg_i_nimin2 0x1 NIMIN2番を信号線へアサインします。
Reg_i_nimin3 0x2 NIMIN3番を信号線へアサインします。
Reg_i_nimin4 0x3 NIMIN4番を信号線へアサインします。
Reg_i_default 0x7 このレジスタが設定された場合、指定のデフォルト値がそれぞれの内部信号線へ代入されます。

以下はIOMレジスタの初期値のテーブルです。

NIM出力ポート 初期レジスタ
NIMOUT1 Reg_o_ModuleBusy
NIMOUT2 reg_o_RML1
NIMOUT3 reg_o_RML2
NIMOUT4 reg_o_RMClr
内部信号線 初期レジスタ デフォルト値
ExtL1 Reg_i_Nimin1 NIMIN1
ExtL2 Reg_i_default 0
ExtLClear Reg_i_default 0
ExtLBusy Reg_i_nimin3 NIMIN3
ExtLRsv2 Reg_i_nimin4 NIMIN4
cntRst Reg_i_default 0
PiKFlag Reg_i_nimin2 NIMIN2

HUL上のスイッチ・LEDの機能

DIP SW2の機能
HUL RMと同様です。

LED点灯の機能
HUL RMと同様です。

DAQの動作

Mass triggerからはLR-TDCとHR-TDCの測定結果、およびlevel2判定の結果(フラグ)が返ってきます。Level2判定はイベント毎に行うため、level2判定を行っている間BUSYになります。

Module Busyとなるタイミング
BUSYの定義は以下に列挙するBUSY信号のORになります。

BUSY種別 BUSY長 備考
Self busy 210 ns L1 triggerを検出した瞬間から固定長でアサート。
Sequence busy サーチ窓幅に依存 Ring bufferからヒット情報を探している間、すなわち`WindowMax`-`WindowMin`分のBUSYが出力されます。Mass triggerにはLR-TDCとHR-TDCが存在するため、長いほうが採用されます。
Block full - ブロックバッファがfullになった段階でBUSYが出力されます。L1 triggerレートが後段の回路のデータ処理速度を上回るとアサートされます。つまりTCP転送が追いつかない事を意味するので、実質的にSiTCP fullと同等です。
SiTCP full - SiTCPのTCPバッファがFullになると出力されます。ネットワーク帯域に対してEvent Builderが送信しようとするデータ量が多いとアサートされます。
Decision busy `MST::TimerPreset`に依存 Level1 trigger受信からlevel2/clear出力までの間BUSYになります。`MST::TimerPreset`に依存します。

データ構造
ヘッダワード

Header1 (Magic word)
MSB                                                                                          LSB
|                                           0xFFFF20D1                                         |

Header2 (event size)
|       0xFF00       |  OerFlow  |    "000"    |         Number of word (12-bit)               |

Number of wordはデータボディに含まれるワード数を示します。Number of WordはSub-header分の2ワード分を含みます。なので最低値が2です。Over flowはHUL全体で1chでもover flowチャンネルがあると立ちます。

Header3 (event number)
|   0xFF   | HRM bit | "000" |  Tag (4-bit)  |             Self counter (16-bit)               |

TagはTRMから出力される4bitのTag情報です。下位3bitがRM Event Numberの下位3ビット、4ビット目がRM spill numberの最下位ビットとなります。Self-counterはイベント転送を行うたびにインクリメントされるlocal event numberで、0オリジンです。

Data body
RVM data
|  0xF9  | "00" |  Lock  |  SNI  |  Spill Num (8-bit))  |           Event Num (12-bit)         |

Mass trigger data
|                 0x2000                    |   "0000'0000'0"   |   Mass trigger flag (7-bit)  |

HR-TDC block
Sub-hearder
|  0x8000  | "00" |  OerFlow  |  StopDuout  |  Through  |           # of word (11-bit)         |
HR-TDC data
|  Magic word (3-bit)  |  Ch (5-bit)  |                     TDC (24-bit)                       |

LR-TDC block
Sub-hearders
|  0xFC10  | "00" |  OerFlow  |  StopDuout  |  Through  |           # of word (11-bit)         |
|  0xFC20  | "00" |  OerFlow  |  StopDuout  |  Through  |           # of word (11-bit)         |
LR-TDC data
|   0xCC   |  "0"  |   Ch (7-bit)   |   "00000"   |                 TDC (11-bit)               |

データボディ領域ではsub-headerに続いてその領域のデータが返ってきます。

Mass trigger flagの内訳

ビット番号 フラグ
0 No decision
1 Level2
2 Fast clear
3 Consolation accept
4 Final clear
5 Accept
6 Clear

Streaming TDC

固有名 0x11dc
メジャーバージョン 0x03
マイナーバージョン 0x05

更新歴

バージョン リリース日 変更点
v3.5 2021.4.

動作概要
このファームウェアはtrigger-less DAQ用に開発された外部トリガー無しに連続的に時間測定を行うTDCです。J-PARC MRの遅い取り出しの2秒間の間、1 nsの精度で時間測定を行うことを想定しています。Trigger-less DAQではフロントエンド回路上でトリガーによるイベント選別を行わないため、入力信号全てをデジタイズしPCへデータ転送を続けます。

HULはtrigger-less DAQにおいてdata streamingを行うにはデータリンクスピードが不十分であり、また十分なメモリ搭載していません。このファームウェアは連続時間測定の技術実証のために開発した側面が強いです。今後HULではこのファームウェアの開発は継続せず、AMANEQというtrigger-less DAQ用に開発された回路に引き継ぐ予定です。Trigger-less DAQや連続読み出しに興味のある方は本多へ連絡をお願いいたします。

このような背景があるので、このファームウェアには試験的に実装した機能も存在します。ここでは汎用的に使えそうな部分のみ説明することにします。

ブロック構造
入力はmain-inの上側を利用します。そのほか、テスト入力、VETO入力、スピルゲート入力をNIMINポートから行います。本TDCのチャンネル数は32 chです。テスト入力が有効の場合、main in Uの入力の代わりにNIMIN2からの信号が全チャンネルに配られます。高繰り返しのテスト信号を入れるとデータレートがすぐにリンクスピードを上回るので、利用時にはレートに気を付けてください。VETO入力はHIGHの間入力信号をマスクします。スピルゲートよりもさらに細かく入力信号の選択をしたい場合に利用してください。スピルゲートはJ-PARCの遅い取り出しのスピルゲートを想定しています。スピルゲートがHIGHの状態の時だけ、本TDCはデータを送信します。本TDCは端的にはスピルスタートからの時間を連続的に測るTDCです。そのため、スピルゲートは2秒間ONで2秒間OFFのように周期的にやってくることが前提になっています。

時間計測Online Data Processing (ODP) blockで行われます。ここで入力信号の立ち上がりと立下りの両エッジの時間を測定し、エッジペアを見つけます。この段階でTime-Over-Thresholdが計算され、立下りの時刻情報は破棄されます。以後、データワード内には立ち上がり時刻とTOT値が含まれます。

ODPブロックまでは各チャンネル毎に独立にデータ処理されます。Vital blockではデータパスを1つにまとめ上げ、データ列へハートビートデータという特殊データの挿入を行います。本TDCのコースカウントは125 MHzのクロックで駆動されている16-bitカウンタ (heartbeat generator)によって付与され、500 μs程度で1周します。それ以上の長さで時刻再構成を行うために、heartbeat methodという方式を導入しています。Heartbeat generatorが1周するごとにデータ列にheartbeatデータを挿入します。解析ではheartbeatデータの数を数えることで、スピルスタートからの時間を再構成することが出来ます。Heartbeatデータはデータ列のちょうど区切りの位置に挿入されなければならないため、vital blockにはtime frameの切れ目を見つける工夫が施されています。

データレートがSiTCPのスピードを超えた場合の対処など、さらに詳しい情報は参考文献を参照してください。(R.Honda et al., PTEP, 2021)

block-strtdc-fw

Streaming TDC仕様
TDC精度 0.97... ns
最長スピルゲート長 33秒
最小パルス幅 ~4 ns
最大パルス幅 150 ns
ダブルヒット分解能 ~7 ns

レジスタマップ

TOT filerとtime-walk correctorはこのUGの中では説明していません。もし利用する場合は参考文献を読んでください。

レジスタ名 アドレス 読み書き ビット幅 備考
DAQ Controller: DCT (module ID = 0x0)
SelectTrigger 0x0000'0000 R/W 12 DAQデータ取得を開始するためのゲート。
Online Data Processing block: ODP (module ID = 0x1)
EnFilter 0x1000'0000 R/W 1 TOT filterの機能を有効にします。
MinTh 0x1010'0000 R/W 8 TOT filterの下限閾値を設定します。この値よりTOTが小さいとフィルターされます。
MaxTh 0x1020'0000 R/W 8 TOT filterの上限閾値を設定します。この値よりTOTが大きいとフィルターされます。
EnZeroThrough 0x1030'0000 R/W 1 TOT値が0だったヒット(立下りエッジが見つからなかったヒット)をフィルターしないようにします。
TwCorr0 0x1040'0000 R/W 8 Time-walk correctorの領域0の補正値を設定します。
TwCorr1 0x1050'0000 R/W 8 Time-walk correctorの領域1の補正値を設定します。
TwCorr2 0x1060'0000 R/W 8 Time-walk correctorの領域2の補正値を設定します。
TwCorr3 0x1070'0000 R/W 8 Time-walk correctorの領域3の補正値を設定します。
TwCorr4 0x1080'0000 R/W 8 Time-walk correctorの領域4の補正値を設定します。

HUL上のスイッチ・LEDの機能

DIP SW2の機能

スイッチ番号 機能 詳細
1 SiTCP force default ONでSiTCPのデフォルトモードで起動します。電源投入前に設定している必要があります。
2 Enable test in ONにするとNIMIN2が全チャンネルの入力に接続されます。
3 MCD mode bit-1 MCDメザニンを搭載した際の動作を決めるビットです。通常はOFF (0)に設定します。
  • 0b11: Master
  • 0b10: Repeater
  • 0b01: Slave
  • 0b00: Stand alone
4 MCD mode bit-2 MCDメザニンを搭載した際の動作を決めるビットです。通常はOFF (0)に設定します。
5 Enable signal copy このビットがONだと、下側のメザニンコネクタへ入力信号のコピーが出力されます。別の回路でも信号を使いたい時に利用します。DTLメザニンカードを下側のメザニンスロットへ取り付けてください。
6 Not in Use
7 Not in Use
8 Not in Use

LED点灯の機能

LED番号 備考
LED1 点灯中はTCP接続が張られています。
LED2 機能していません。
LED3 点灯中はスピルゲート入力がHIGHであることを示します。
LED4 機能していません。

NIM-IOへの信号アサイン
Streaming TDCにはIOMが存在しないため、入出力のアサインを変える事はできません。

NIMIO 備考
NIM-IN
NIN-IN1 スピルゲート入力。
NIM-IN2 テスト入力。
NIM-IN3 VETO入力。
NIM-IN4 未使用
NIM-OUT
NIM-OUT1 未使用
NIM-OUT2 未使用
NIM-OUT3 NIM-IN1に入力されたスピルゲートのコピー出力。クロック同期を取った後の信号のため立ち上がりタイミングは量子化されている。
NIM-OUT4 未使用

DAQの動作

Streaming TDCはtirgger-less DAQで使用することを想定しているため、データ取得のトリガーという概念は存在しません。 データ転送を行う条件が揃うとFPGA即座にネットワークにデータを送信しようと試みるため、PC側は先にデータ準備が出来ていないといけません。 FPGAがデータを出力する条件は次の3つが全て成立している事です。 1. TCP connectionが成立している。 2. DAQ gateがONになっている。 3. Spill gateがON (NIMIN1の信号がHIGHである)。 本FWを使用する際には、上記順番の通りに処理することをお勧めします。 DAQ gateがONでspill gateがONになるとODPブロックはデータ計測を開始します。 この時点でTCP接続が確立していないと内部バッファにデータが溜まり続けていくため、バッファがあふれてしまう可能性があります。 TCP接続を確立してからRBCPでDAQ gateをONにしてください。

データ構造
Streaming TDCの1ワードは40-bitです。受け取ったデータをそのままint32_tint64_tにキャストできないので、ソフトウェアの記述は工夫してください。 本FWにはspill start, TDC data, heartbeat, busy, spill endの5種類のデータが存在します。 それぞれ先頭の4ビットで識別が可能です。 Heartbeatデータはheartbeat (time) frameの境目に挿入され、spill startから何回目のheartbeatであるかを示すカウンターが下位16-bitに埋め込まれています。 もしvital blockの状態がbusyモードの場合にはheartbeatデータの代わりにbusyデータが返ってきます。

Spill start word
MSB                                                                                          LSB
|      0x1      |           RSV (20-bit)              |                  0xFFFF                |

TDC data
|      0xD      | '0' | TOT(8-bit) | Type(2-bit) | Ch(6-bit) |            TDC(19-bit)          |

Heartbeat data
|      0xF      |           RSV (20-bit)              |         heartbeat number (16-bit)      |
Busy data
|      0xE      |           RSV (20-bit)              |         heartbeat number (16-bit)      |

Spill end data
|      0x4      |           RSV (20-bit)              |                  0xFFFF                |

TDC dataに含まれるtypeは現状きちんと機能していません。 通常のTDC dataであれば00です。そのほかに0110のパターンがありますが、これらであった場合そのデータは無視してください。

Busyモード
FPGAが送信しようとするデータ量がデータリンクのスピードを超えると転送が追い付かなくなり、FPGA内部のバッファが溢れます。 このような状況にFWが陥ると、vital blockは通常の動作モードからbusyモードへ状態を遷移させ復帰を試みます。 Streaming TDCではtriggerを止めるためのBUSY信号は存在しませんが、busyモードではbusyデータがheatbeatデータの代わりに現れるようになります。 Busyデータが返ってきたheartbeatフレームではデータ欠落が起きていますが、どのデータをどれだけ落としたかは分かりません。 一部または全てのデータが欠落しているということだけが分かります。 一旦busyモードに移行すると最低3フレーム復帰するために必要とします。 更に詳しい動作については参考文献を参照してください。

データの並び
Streaming TDCから出力されるデータの並びを時間軸上に表した物をに示します。 Spill gateの立ち上がりを検出するとまずspill start dataが出力されます。 次に最初のheatbeat frame内のTDC dataが続き、frameの境目にheartbeat (busy) dataが挿入されます。 Busy dataが返ってきた場合該当frameではデータ欠落が起きています。

data-order-strtdc