2133005_ja-JP

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

2133005_ja-JP

2133005_ja-JP

NHS3152 パッシブ測定

やあみんな

カスタム PCB 上に NHS3152 が搭載されています。PCB は非常にシンプルで、MCU-Link Pro 用の SWD コネクタと、スクリーン印刷されたアンテナに接続するためのコネクタへのトレースがいくつか付いています。電力の安定性を確保するため、ピン 3 とピン 7 の両方に 2 つの 100nF コンデンサが並列に接続されています (合計 4 つのコンデンサ)。

抵抗測定に関して問題があります。抵抗測定用のチャネルが 2 つあります (チャネル 0 = ピン 0、1、チャネル 1 = ピン 4、5)。ボードがパッシブに実行されているとき (デバッガーから電源が供給されていないとき) に抵抗測定を実行すると、NFC スキャナー (Arduino Uno 用の Adafruit PN532 シールド) はデータを受信しません。ただし、NHS3152 がデバッガーから電力を受け取っている場合は、測定から正しいデータを受信します。

抵抗測定に関連するコードのセクションを無効にすると、NFC の内容を正常に読み取ることができるので、ADC が電力を消費しすぎているのではないかと思います。


これに関してご助力いただければ幸いです。


IDE: MCUXpresso v24.9.25

SDK: release_mra2_12_6_nhs3152


読み取り失敗時のスキャナーからの出力(パッシブ モードで実行中):

=================================================
タグが見つかりアクティブ化されました!データの読み取りを準備しています。
UIDの長さ: 7バイト
UID値: 0x04 0x8E 0xE6 0x00 0xA8 0x00 0x10
----------------------------------------
8~12ページからのデータの読み取り
8ページを読み取れませんでした

=================================================
タグが失われたか、通信に失敗しました。リセットしています...
=================================================


デバッガー経由でNHS3152に電源が投入されたときのスキャナーからの出力:

=================================================
タグが見つかりアクティブ化されました!データの読み取りを準備しています。
UIDの長さ: 7バイト
UID値: 0x04 0x8E 0xE6 0x00 0xA8 0x00 0x10
----------------------------------------
8~12ページからのデータの読み取り
ページ08: 6E 52 31 3A nR1:
ページ09: 34 2C 52 32 4,R2
ページ10: 3A 2D 31 FE :-1
ページ 11: 86 56 4D 3D VM=
ページ 12: 84 28 57 0C (W.
データの読み取りに成功しました。タグはまだ残っています。
----------------------------------------


NHS3152


メイン.c:


/*

* ジェームズ・ハロルド、2025年、サイオン

*

* このプログラムは2つの別々のアナログチャネルで抵抗を測定します

* 結果を NFC タグに書き込み、ワイヤレスで読み取ります。

*

*/


// 1. ライブラリのインポート

#include "board.h"

#include "ndeft2t/ndeft2t.h"

#include

#include "pmu_nss.h"

#include "gpio_nss.h"

#include

#include

#include


// 2. 定義

#define CHANNEL_0 0 // 容量性および抵抗性チャネル

#define CHANNEL_1 1 // 抵抗チャネル

#define NUM_CHANNELS 2 // 測定チャネルの総数


// 3. グローバル変数


// NDEFメッセージ作成用のバッファ(NFC用)

静的uint8_t g_ndeft2tInstanceBuffer[NDEFT2T_INSTANCE_SIZE] __attribute__ ((aligned (4)));

静的uint8_t g_nfcMessageBuffer[NFC_SHARED_MEM_BYTE_SIZE] __attribute__ ((aligned (4)));


// 各測定チャネルの結果を格納する配列

揮発性int32_t 測定抵抗[NUM_CHANNELS] = {0, 0};


// 4. NFCコールバック(ライブラリで必須だが未使用)

void NDEFT2T_FieldStatus_Cb (bool ステータス) { ( void )ステータス; }

void NDEFT2T_MsgAvailable_Cb ( void ) { /* 未使用 */ }


// 5. 関数プロトタイプ

voidセットアップ電力安定化( void );

voidセットアップ抵抗測定( intチャネル);

int32_t PerformAndCalculateResistance ( intチャネル);

void WriteMeasurementsToNFC (int32_t res1、int32_t res2);

void WriteHelloMessageToNFC ( void );


// 6. メインコード

int main ( void ) {


// ステップ1: 最小限のボードと電源のセットアップを実行する

ボード初期化();

SetupPowerStabilisation (); // NFCタグからのエネルギー収集のためには早めに実行する必要がある


// --- 使用するペリフェラルのクロックと電源を有効にする ---

Chip_Clock_Peripheral_EnableClock( CLOCK_PERIPHERAL_ADCDAC | CLOCK_PERIPHERAL_I2D );

Chip_SysCon_Peripheral_EnablePower( SYSCON_PERIPHERAL_POWER_ADCDAC | SYSCON_PERIPHERAL_POWER_I2D );


// 電源とクロックが安定するまでの小さな遅延

チップクロックシステムビジーウェイトus(100);


// --- 抵抗測定の初期化 ---

// ペリフェラルを初期化し、アナログピンを設定する

Chip_ADCDAC_Init(NSS_ADCDAC0);

Chip_I2D_Init(NSS_I2D);


// Configure チャネル0のアナログピンを設定する(ANA0_0、ANA0_1)

Chip_IOCON_SetPinConfig(NSS_IOCON、 IOCON_ANA0_0 、IOCON_FUNC_1);

Chip_IOCON_SetPinConfig(NSS_IOCON、 IOCON_ANA0_1 、IOCON_FUNC_1);


//チャネル1のアナログピン(ANA0_4、ANA0_5)を設定します

Chip_IOCON_SetPinConfig(NSS_IOCON、 IOCON_ANA0_4 、IOCON_FUNC_1);

Chip_IOCON_SetPinConfig(NSS_IOCON、 IOCON_ANA0_5 、IOCON_FUNC_1);


// ADCを狭い電圧範囲(1.0V)に設定します

Chip_ADCDAC_SetInputRangeADC(NSS_ADCDAC0、 ADCDAC_INPUTRANGE_NARROW );


// ステップ 2: NFC 通信を初期化する

Chip_NFC_Init(NSS_NFC);

NDEFT2T_Init();


// ステップ3: 抵抗測定を実行する

抵抗測定を設定します(CHANNEL_0);

測定抵抗[CHANNEL_0] = PerformAndCalculateResistance(CHANNEL_0);


抵抗測定を設定します(CHANNEL_1);

測定された抵抗[CHANNEL_1] = PerformAndCalculateResistance(CHANNEL_1);


// ステップ4: 測定値をNFCタグに書き込む

測定抵抗をNFCに書き込みます(測定抵抗[CHANNEL_0]、測定抵抗[CHANNEL_1])。

//HelloMessageをNFCに書き込みます();


// --- 使用後はペリフェラルの電源を切って電力を節約する ---

Chip_SysCon_Peripheral_DisablePower( SYSCON_PERIPHERAL_POWER_ADCDAC | SYSCON_PERIPHERAL_POWER_I2D );

Chip_Clock_Peripheral_DisableClock( CLOCK_PERIPHERAL_ADCDAC | CLOCK_PERIPHERAL_I2D );


// ステップ5: NFCペリフェラルの割り込みを待つ

(1) { {

__WFI();

}


return 0; // 決して到達してはならない

}


// 7. 関数宣言


/**

* @brief 特定のチャネルでの抵抗測定用にハードウェアを構成します。

* @param channel : 設定する測定チャネル(CHANNEL_0 または CHANNEL_1)

* @return 何も返さない

*/

voidセットアップ抵抗測定( intチャネル) {

ADCDAC_IO_T dac_pin;

I2D_INPUT_T i2d_ピン;


if (チャネル == CHANNEL_1) {

dac_pin = ADCDAC_IO_ANA0_4 ;

i2d_pin = I2D_INPUT_ANA0_5 ;

}

それ以外{

dac_pin = ADCDAC_IO_ANA0_0 ;

i2d_pin = I2D_INPUT_ANA0_1 ;

}


Chip_ADCDAC_SetMuxDAC(NSS_ADCDAC0、dac_pin);

Chip_ADCDAC_WriteOutputDAC(NSS_ADCDAC0, 0xFFF); // DAC出力電圧を下げるために0xFFFから0x800に変更しました

Chip_I2D_SetMuxInput(NSS_I2D、i2d_pin);


if (チャネル == CHANNEL_0) {

Chip_I2D_Setup(NSS_I2D, I2D_SINGLE_SHOT , I2D_SCALER_GAIN_100_1 , I2D_CONVERTER_GAIN_LOW , 10); // I2D変換周期を100から10に変更(省電力)

}

それ以外{

Chip_I2D_Setup(NSS_I2D, I2D_SINGLE_SHOT , I2D_SCALER_GAIN_100_1 , I2D_CONVERTER_GAIN_LOW , 10); // I2D変換周期を100から10に変更(省電力)

}


// 電圧と電流が安定するまでしばらく待ちます。

チップクロックシステムビジーウェイトms(1);

}


/**

* @brief 電力の安定性のためにコンデンサ バンクを有効にするために GPIO を初期化します。

* @return 何も返さない

* @note これはパッシブ操作にとって最も重要な初期化です。

*/

voidセットアップ電力安定化( void ) {


Chip_IOCON_Init(NSS_IOCON);

Chip_GPIO_Init(NSS_GPIO);


// --- フェーズ 1: プリチャージ ---

// 内部プルアップ抵抗を有効にしてピンを入力として設定します。

// これにより、電圧降下を引き起こすことなく、外部キャップをゆっくり充電できるようになります。


Chip_IOCON_SetPinConfig(NSS_IOCON, IOCON_PIO0_3 , IOCON_FUNC_0 | IOCON_RMODE_PULLUP); // ピン3をGPIOとして設定し、プルアップを有効にする

Chip_GPIO_SetPinDIRInput(NSS_GPIO, 0, 3); // ピン3を入力として設定する


Chip_IOCON_SetPinConfig(NSS_IOCON, IOCON_PIO0_7 , IOCON_FUNC_0 | IOCON_RMODE_PULLUP); // ピン7をGPIOとして設定し、プルアップを有効にする

Chip_GPIO_SetPinDIRInput(NSS_GPIO, 0, 7); // ピン7を入力として設定する


// コンデンサが充電されるまで少し待ちます。

Chip_Clock_System_BusyWait_ms(60); // 4つの時定数で60ms(各ピンに200nFが接続されています)


// --- フェーズ2: エンゲージ ---

// キャップが充電されたので、安全に電源レールに接続CAN

// ピンを OUTPUT に設定し、HIGH に駆動します。


Chip_IOCON_SetPinConfig(NSS_IOCON, IOCON_PIO0_3 , IOCON_FUNC_0 | IOCON_RMODE_INACT); // ピン3をGPIOとして設定し、プルアップを無効にします

Chip_GPIO_SetPinDIROutput(NSS_GPIO, 0, 3); // ピン3を出力として設定する

Chip_GPIO_SetPinOutHigh(NSS_GPIO, 0, 3); // ピン3をHighに設定してVDDレールに接続します


Chip_IOCON_SetPinConfig(NSS_IOCON, IOCON_PIO0_7 , IOCON_FUNC_0 | IOCON_RMODE_INACT); // ピン7をGPIOとして設定し、プルアップを無効にします

Chip_GPIO_SetPinDIROutput(NSS_GPIO, 0, 7); // ピン7を出力として設定する

Chip_GPIO_SetPinOutHigh(NSS_GPIO, 0, 7); // ピン7をHighに設定してVDDレールに接続します

}


/**

* @brief 2 つの抵抗値を含む NDEF メッセージを作成し、メモリに書き込みます。

* @ param res1: 最初のチャネルからの生の抵抗値。

* @ param res2: 2 番目のチャネルからの生の抵抗値。

* @return 何も返さない

*/

void WriteMeasurementsToNFC (int32_t res1, int32_t res2) {

charペイロードテキスト[64];

NDEFT2T_CREATE_RECORD_INFO_Tレコード情報を作成します。

uint8_t ロケール[] = " en " ;


snprintf(payloadText, sizeof (payloadText), "R1: %ld,R2:% ld " , res1, res2);


NDEFT2T_CreateMessage(g_ndeft2tInstanceBuffer、g_nfcMessageBuffer、

NFC_SHARED_MEM_BYTE_SIZE、true);


createRecordInfo.shortRecord = 1 ;

createRecordInfo.pString = ロケール;


if (NDEFT2T_CreateTextRecord(g_ndeft2tInstanceBuffer, &createRecordInfo)) {

if (NDEFT2T_WriteRecordPayload(g_ndeft2tInstanceBuffer, (uint8_t*)payloadText,

strlen(ペイロードテキスト))) {

NDEFT2T_CommitRecord(g_ndeft2tInstanceBuffer);

}

}


NDEFT2T_CommitMessage(g_ndeft2tInstanceBuffer);

}


/**

* @brief シンプルな NDEF テキスト メッセージ「hello」を作成し、NFC メモリに書き込みます。

* @return 何も返さない

*/

void WriteHelloMessageToNFC ( void ) {

char payloadText[] = "バナナ" ;

NDEFT2T_CREATE_RECORD_INFO_Tレコード情報を作成します。

uint8_t ロケール[] = " en " ;


// 1. バッファ内に新しい NDEF メッセージの作成を開始します。

NDEFT2T_CreateMessage(g_ndeft2tInstanceBuffer、g_nfcMessageBuffer、

NFC_SHARED_MEM_BYTE_SIZE、true /* 最初のメッセージです */ );


// 2. 新しい NDEF テキスト レコードの情報を準備します。

createRecordInfo.shortRecord = 1 ;

createRecordInfo.pString = ロケール;


// 3. メッセージ内にテキスト レコード構造を作成します。

if (NDEFT2T_CreateTextRecord(g_ndeft2tInstanceBuffer, &createRecordInfo)) {


// 4. 実際の「hello」文字列をレコードのペイロードに書き込みます

if (NDEFT2T_WriteRecordPayload(g_ndeft2tInstanceBuffer, (uint8_t*)payloadText,

strlen(ペイロードテキスト))) {


// 5. この特定のレコードを確定します。

NDEFT2T_CommitRecord(g_ndeft2tInstanceBuffer);

}

}


// 6.メッセージ全体を確定し、NFC ハードウェアで使用できるようにします。

NDEFT2T_CommitMessage(g_ndeft2tInstanceBuffer);

}


/**

* @brief ADC および I2D 変換を実行し、特定のチャネルの抵抗を計算します。

* @param channel : 測定する測定チャネル(CHANNEL_0 または CHANNEL_1)

* @return 生のスケーリングされた抵抗値、またはエラーが発生した場合は -1 (例: オープン サーキット)。

* @note 低電力の __WFE() を使用して変換を待機します。これはパッシブ モードに不可欠です。

*/

int32_t PerformAndCalculateResistance ( intチャネル) {

int32_t v_drive、v_sense、i2d_val、adc_diff、result;

ADCDAC_IO_Tドライブピンadc、センスピンadc;


/*

* 注意: ペリフェラルクロックと電源は main() で有効になっているものと想定されます。

* この関数が複数の場所から呼び出される場合は、有効/無効にすることができます

* 代わりにここに記載してください。このアプリケーションでは、main() で有効にする方が効率的です。

*/


if (チャネル == CHANNEL_1) {

ドライブピンadc = ADCDAC_IO_ANA0_4 ;

sense_pin_adc = ADCDAC_IO_ANA0_5 ;

}

それ以外{

ドライブピンadc = ADCDAC_IO_ANA0_0 ;

sense_pin_adc = ADCDAC_IO_ANA0_1 ;

}


// --- V_DRIVE ADC測定 ---

Chip_ADCDAC_SetMuxADC(NSS_ADCDAC0、ドライブピンadc);

Chip_ADCDAC_StartADC(NSS_ADCDAC0);

// 新しい低電力の方法: ADC 変換が完了するまでスリープします。

while (!(Chip_ADCDAC_ReadStatus(NSS_ADCDAC0) & ADCDAC_STATUS_ADC_DONE )) {

{ /* 待って */ }

}

v_drive = Chip_ADCDAC_GetValueADC(NSS_ADCDAC0);


// --- V_SENSE ADC測定 ---

Chip_ADCDAC_SetMuxADC(NSS_ADCDAC0、sense_pin_adc);

Chip_ADCDAC_StartADC(NSS_ADCDAC0);

// ADC 変換が完了するまでスリープします。

while (!(Chip_ADCDAC_ReadStatus(NSS_ADCDAC0) & ADCDAC_STATUS_ADC_DONE )) {

{ /* 待って */ }

}

v_sense = Chip_ADCDAC_GetValueADC(NSS_ADCDAC0);


// --- I2D測定 ---

Chip_I2D_Start(NSS_I2D);

// I2D 変換が完了するまでスリープします。

while (!(Chip_I2D_ReadStatus(NSS_I2D) & I2D_STATUS_CONVERSION_DONE )) {

{ /* wait */ } // イベント情報を待機 - ADC_DONE イベント情報で起動 --> __WFE() をビジー待機に置き換えました {}

}

i2d_val = Chip_I2D_GetValue(NSS_I2D);


/*

* 注意: 次の測定ではペリフェラルの電源はオンのままになります。

* main() の終了時に電源がオフになります。

*/


// --- 計算 ---

adc_diff = v_drive - v_sense;

(adc_diff < 1)の場合{

adc_diff = 1;

}


i2d_val > 0 の場合{

抵抗結果 = ((uint32_t)adc_diff * 10000) / i2d_val;

}

それ以外{

resistance_result = -1; // 断線またはエラーを示します

}


resistance_resultを返します

}


ntag2xx_read.ino:


/********************************************************************************/
/*!
    @ファイルreadntag_continuous_power_and_data.ino
    @author KTOWN (Adafruit Industries) / 連続電源とデータ読み取り用に改造
@license BSD (license.txt を参照)

このバージョンではパッシブNFCタグに継続的に電力が供給され、
ループでは、特定の範囲のページ (8 ~ 13) からデータを読み取って表示します。
タグが削除されるとリセットされます。
*/
/********************************************************************************/
#include
#include
#include

// SPI でブレークアウトを使用する場合は、SPI 通信用のピンを定義します。
#PN532_SCK (SCK)を定義します
#define PN532_MISO (MISO)
#PN532_MOSI (MOSI)を定義します
#define PN532_SS (10) // または使用しているSPI CSピン

// I2Cでブレークアウトまたはシールドを使用する場合は、I2Cのピンを定義します
// SPI 定義をコメント アウトします。
# PN532_IRQを定義する(2)
#PN532_RESETを定義する(3)

// この行をI2Cに使用します
Adafruit_PN532 nfc (PN532_IRQ、PN532_RESET);

// またはSPIの場合はこの行を使用します
// Adafruit_PN532 nfc(PN532_SCK、PN532_MISO、PN532_MOSI、PN532_SS);


// タグが現在選択されているかどうかを追跡するグローバル状態変数
ブールtagIsPresent = false ;
uint8_t uid[] = { 0 , 0 , 0 , 0 , 0 , 0 , 0 };
uint8_t uid長さ;
intページ開始 = 8 ;
intページ終了 = 12 ;

voidセットアップ( void ) {
  シリアル.begin ( 115200 ) ;
  while (!Serial) delay ( 10 ); // Leonardo/Micro/Zeroの場合

  nfc .begin ( );
  uint32_t versiondata = nfc.getFirmwareVersion ( ) ;
  if (!versiondata) {
    シリアル.print ( "PN53xボード見つかりませんでした" );
    while ( 1 ); // 停止
  }
  Serial.print ( "チップPN5が見つかりました" ) ; Serial.print ( (versiondata >> 24 ) & 0x FF , HEX);
  Serial.print ( ",ファームウェアバージョン " ) ; Serial.print ((versiondata >> 16 ) & 0x FF , DEC );
  シリアル.print ( '.' );シリアル.println ( (versiondata >> 8 ) & 0x FF , DEC );

// ISO14443A カードをリッスンするようにボードを構成する
  nfc.SAMConfig ( ) ;

  シリアル.println ( "ISO14443Aカードの電源と読み取りを待機しています..." ) ;
}

void loop ( void ) {
  // === 状態 1: タグが選択されていません ===
// タグがない場合は、タグを探します。
  タグが存在する場合{
    Serial.print ( "." ); // 待機中であることを示すドットを出力ます

// カードがフィールドに入るのを待ちます。これによって電力も供給されます。
    bool成功 = nfc . readPassiveTargetID (PN532_MIFARE_ISO14443A, uid, &uidLength, 500 );

    (成功)の場合{
tagIsPresent = true ;
      シリアル.println ( " \n============================================================" );
      シリアル.println ( "タグが見つかりアクティブ化されました。データの読み取りを準備しています。" ) ;
      Serial.print ( "UID長さ:" ) ; Serial.print ( uidLength ,DEC); Serial.println ( "バイト" ) ;
      シリアル.print ( "UID値:" ) ;
      nfc . PrintHex (uid, uidLength);
     
// オプションの遅延: タグがセンサで、
// 電源投入後に測定を実行する場合は、ここで遅延を追加します。
// 多くのセンサ タグの場合、200 ミリ秒が適切な開始点です。
      遅延 200 );
   }
// 失敗またはタイムアウトした場合は、ループが再開され、再試行されます。
    戻る;
  }

  // === 状態 2: タグが選択され、電源が投入されています ===
// タグがある場合は、ページ 8 から 13 までのデータを読み取ろうとします。
  (タグが存在する)の場合{
    シリアル.println ( "----------------------------------------" ) ;
    シリアル.print ( "ページからデータを読み込んでいます" ) ;
    シリアル.print (pageStart) ;
    シリアル.print ( "-" ) ;
    シリアル.print ( pageEnd);
    シリアル.println ( );
   
    ブール値all_reads_succeeded = true ;
   
    for ( int page = pageStart; page <= pageEnd; page++) {
      uint8_t page_data [ 4 ]; // NTAGページは4バイト長です
     
// 現在のページを読み取ろうとする
      if ( nfc . ntag2xx_ReadPage (ページ、ページデータ)) {
// 成功!データを印刷します。
        シリアル.print ( "ページ" );
        if (page < 10 ) Serial . print ( "0" ); // きれいに整列させる
        シリアル.印刷(ページ);
        シリアル.print ( ": " ) ;
// nfc.PrintHexCharは16進数とASCIIコードを出力する優れたヘルパー関数です
        nfc . PrintHexChar (page_data, 4 );
}それ以外{
// 読み取りに失敗しました!これはタグが削除されたことを示す信号です。
        Serial.print ( "ページ読み取りに失敗しました" ) ; Serial.println ( page );
all_reads_succeeded = false ;
        break ; // forループを直ちに終了する
     }
   }

    すべての読み取りが成功した場合{
      シリアル.println ( "データ読み取りに成功しました。タグはまだ存在します。" );
}それ以外{
// 読み取りに失敗した場合は、システム状態をリセットします。
      シリアル.println ( " \n============================================================" );
      シリアル.println ( "タグが失われたか通信失敗しました。リセットしています..." );
      シリアル.println ( "============================================================" ) ;
tagIsPresent = false ; // 状態をリセットする
      nfc . SAMConfig (); // 新しいタグをリッスンするようにリーダーを再設定する
   }
   
// 次の読み取りサイクルの前に少し待機します。
    遅延 2000年);
  }
}
Re: NHS3152 Passive Measurement

ご参考までに。

NHS3152 は NFC フィールドと負荷コンデンサからのみ電力供給されます - NXP コミュニティ

Re: NHS3152 Passive Measurementこんにちは、ジミーさん。返信ありがとうございます。コンデンサ バンクにさらに静電容量を追加すると、パッシブ モードでの ADC 動作が可能になると思われますか?もしそうなら、これらの操作を実行するために必要な総静電容量はどれくらいでしょうか。Re: NHS3152 Passive Measurement

ボードがパッシブに動作している場合、ADC の動作に十分な電力が安定しない可能性があります。

Tags (1)
No ratings
Version history
Last update:
‎11-21-2025 06:45 PM
Updated by: