DreamerDreamのブログ

夢想家の夢です。〜揚げたてのモヤっとしたものをラフレシアと共に〜

Linuxの現在時刻を同期させる備忘録

今までサーバーの厳密な時刻設定なんかは必要なくて、数分のズレなんか気にしていませんでした。

 

しかし自作のアプリとの時刻合わせをする用途が出て来たので今更ながらLinuxの時刻同期を行ないます。

 

といっても「chrony」をインストールして起動させるだけです。

<参考>

eng-entrance.com

 

CentOS8ならdnfで、RaspberryPIならapt-getでパッケージインストール

sudo dnf install chrony

・(インストール)

sudo systemctl start chrony

sudo systemctl enable chrony

これだけ。

 

僕の使っているVPSサーバーは実際に約5分の遅れが生じていました。

f:id:DreamerDream:20210623110542p:plain

chromy起動直後のdateコマンドによる確認、少し待つだけで綺麗に現時刻に合わせてくれます。

 

時刻合わせだけでサーバーにしないのなら設定ファイル

/etc/chrony.conf

は特に弄る必要は無い。

 

設定ファイルのこの項目

# Enable kernel synchronization of the real-time clock (RTC).
rtcsync

これで11分おきにリアルタイムクロックと同期してくれるそうです。

 

備忘録でした。

 

 

 

python3のsocket通信で外部からアクセスさせるためには「オールゼロ」”s.bind(( '0.0.0.0' , [ポート番号] )) ”を使う 備忘録

python3で低水準なsocket通信をしようと試みてハマッたことの備忘録です。

 

「python3 socket」等で検索をかけると簡単なsocket通信のサンプルコードが出て来ます。

 

<参考>

【Python3】Pythonでソケット通信を試してみた | DevelopersIO

 

※コードは上記ブログのものをそのまま拝借なのでここでは載せません。

コピペして自分のサーバー内で通信して接続し、「なるほど!」と納得。簡単簡単!

過去にJavaでやったことあるので理解出来ますよ!っと。

さて外部からアクセスしようとすると。。。

 

raceback (most recent call last):
File "test_socket_client.py", line 8, in <module>
s.connect( ( target , 123 ) )
ConnectionRefusedError: [Errno 111] Connection refused

 

というエラーに遭遇しました。

あれ?ポートは開放しているハズなのにおかしいな?

そもそも、

 

この.bindで指定しているIPって何なのさ?

s.bind( ( socket.gethostname() , 123 ) )

 

ということで、このsocket.gethostname()の部分をローカルに変更

[127.0.0.1]

[localhost]

としても繋がらない^^ん〜?

じゃあールーターのアドレス?

[192.168.0.1]

としても繋がらない。。。

じゃあDNS?

[接続先のDNS]

[サーバーのDNS]

[接続先のIPアドレス]

いろいろ試したけど繋がらない・・・

ググってもローカルIPアドレスしか書いて無い!?

なんだこれ???

 

諦めずに調べていくと答えを発見!

teratail.com

 

なんと、通常は「オールゼロ」というIPアドレスを設定するそうです。

[0.0.0.0]

これでOK。

s.bind( (  '0.0.0.0' , 123 ) )

 

ここでようやく意味を理解しました。

ここで設定してるIPアドレスはルーターからLANアダプタに割り振られたIPアドレスのことのようです。

f:id:DreamerDream:20210617165130p:plain

 

なるほど!どのLANアダプタからの情報を繋ぐか?ということなので通常はオールゼロ設定で問題無いですね。

 

こんな事に時間を費やしてしまって悲しい。。

 

 

 

サーボモーターSG90とSG92Rの分解比較 どちらにしようか悩むならSG92Rを購入すべき

 前回、サーボモーターSG90の本物と偽物を分解比較してみました。

dreamerdream.hateblo.jp

 

今回はSG90の強化版SG92RをSG90と比較してみます。

(左:SG90、右SG92R)

f:id:DreamerDream:20210616110610p:plain

 

SG92RはSG90の樹脂ギアにカーボンファイバーを配合した強化ギアになっています。

トルクもSG90が1.8kg/cm(4.8V)のところ、SG92Rは2.5kg/cm(4.8V)となっており、パワーアップしています。

 

SG90の変わりにSG92Rは使えるのか?と気になる方もあることでしょう。

サイズを比較します。

手前がSG92R、奥がSG90です。

f:id:DreamerDream:20210616110619p:plain

うーん、どっからどう見てもパッケージのサイズは「同じ」ように見えます。

f:id:DreamerDream:20210616110629p:plain製品情報を見ると数ミリ違ってたりすることもあるようですが、違いがわかりませんでした。

 

分解します。

本体は同じ4本のネジで止まっています。

f:id:DreamerDream:20210616110639p:plain

制御基板はSG90が赤色、SG92Rが緑色をしているだけで他はほぼ一緒、モーターのサイズも同じようです。

 

ギアの比較

f:id:DreamerDream:20210616110650p:plain

SG92Rが黒いので見辛いですが、

f:id:DreamerDream:20210616110700p:plain

f:id:DreamerDream:20210616110709p:plain

違いが全くわかりません^^。分解した意味・・・

f:id:DreamerDream:20210616110719p:plain

ほぼ一緒!というか全部一緒!!?

 

「こんなんでトルクアップしてるの??」と思いましたが、実際に動かしてみるとSG92Rの方が間違いなくパワーがあります。

 

<SG90でサムターンを回そうとして失敗した動画>

youtu.be

解錠は出来るのですが施錠が出来ません^^;

 

<SG92Rでサムターンを回した動画>

youtu.be

圧倒的ぱわー!!

 

サイズはほぼ同じなので何故?と感じましたが、おそらくギアに応じた強いモーターが使われているのでしょう。

SG90かSG92Rでお悩みの場合、100円程度の差なのでSG92Rを購入しておいた方が後悔が少ないと思います。

 

マイクロサーボ SG92R (1個)

マイクロサーボ SG92R (1個)

  • TOWER PRO(タワープロ)
Amazon

 

 

ちなみに、今回僕は前回記事で書いた通りSG90の偽物を購入し「安物買いの銭失い」を痛感しました。

偽物は本物よりパワーが弱く使い物になりませんでした。

マイクロサーボモーターSG90の本物と偽物を分解して比較してみた 意外と偽物が使えそうな件について

電子工作界隈でマイクロサーボモーターといえば、SG90と言っても過言では無いでしょう。

1こ500円弱の小さなサーボモーターです。

僕もArduinoの入門セット?だかに入っているものが1つだけ手元にありました。

 

以前、実験的に動かしたものです。

dreamerdream.hateblo.jp

 

 

 

 

 

AmazonでSG90を調べてみると結構沢山出て来ますが、こちら4個で1000円のSG90です。

もちろん偽物です。

 

 

今回、こちらの偽物を入手しましたのでその分解レポートです。

 

まず驚いたのがAmazonのページには記載されていなかった「TOWER PRO」というロゴが堂々と入っています。(商標的にアウトですよね・・・)

 

以降、偽物が左側、本物が右側で写真を撮りました。

f:id:DreamerDream:20210605152610p:plain

モーターを止めているネジは本物が4つ、偽物は2つです。

Amazonのサイトではネジ4つ写っていましたので商品写真は本物を使っているようですね。

 

 

f:id:DreamerDream:20210606054521p:plain

皮肉な事に、偽物のケーブルが本物より下の方から出ているので機器として組み込むのには工作がしやすいです。

 

f:id:DreamerDream:20210606054533p:plain

偽物の場合、モーターギリギリのサイズで作ったスペースにもケーブルが下に逃げるので素直に入ります。

f:id:DreamerDream:20210606054543p:plain

本物の場合はギリギリサイズでは通りません。

一度下部を分解することで通す事が出来ます(後で下から底面をネジで止める為に底にも穴が必要です)。

 

f:id:DreamerDream:20210605152559p:plain

そして基板は偽物の方が基板が大きく、本体にしっかり固定されています。

本物の方は本体に止まっておらず、ブラブラしています。

基板だけ見ると偽物の方がしっかりしているように見えます。偽物恐るべし・・・

 

f:id:DreamerDream:20210605152619p:plain

本物と偽物の判別で一番わかりやすい箇所がモーターのギアです。

本物が金属ギアなのに対して偽物はプラスチックです。

 

プラスチックギアだからなのか、偽物の方が音が静かです。

youtu.be

 

f:id:DreamerDream:20210605152630p:plain

サイズはほぼ同じなのですが、偽物の方が本体が若干高いです。(数ミリ程度)

基板が固定されているぶん高くなってるんですかね?

 

f:id:DreamerDream:20210605152638p:plain

しかし、同梱のカム(というのかな?)を接続すると結果として同じぐらいの高さになるようです。(偽物の方が同梱物が薄くてちゃっちい)

 

 

精度は偽物の方が個体差が大きくてラジコンヘリ等には使い物にならないというレビューもありますが、音が小さいことなど用途によっては偽物の方が都合が良いという場合も充分あると思います。

僕は(耐久性は期待出来ませんが)電子工作として使うにはアリじゃないかな?と思いました。

 

 

 

あと、どうやら本物にはPWM信号を切っても3秒ぐらい位置を維持する機能があるようです。(偽物はPWM信号を切ったらすぐニュートラルになります。)

しかし、それが仇となって同じ電力線で繋いでいる他のサーボモーターの電力を奪ってしまうことも・・・

youtu.be

最初はこの動作の意味が解らずプログラムでどうにかしようとしていましたが、信号線を物理的に切断しても3秒ぐらいは位置を保持しているのでサーボモータ側の仕様のようです。

個人的に今作成中のものには完全に不要な機能で困ってるのですが^^; 切る方法が見つかりません。対処としてはサーボモーター2つ同時に動かせる充分な電力を確保するしかないようです。

ちなみに、同じ強化版のSG92R(↓下リンク)にはこの機能はありませんでした。ひょっとして個体差なのかも?(SG90は一個しか所有していないため不明)

 

 追記:偽物の方はパワーが弱いことが判明しました。

dreamerdream.hateblo.jp

 

 

ニンテンドースイッチのジョイコンの構造ってどうなってんの? ジョイコンの中身を分解してみたら・・・

ニンテンドーSwitchのコントローラーのジョイコンの修理依頼を受け、交換修理をしました。

f:id:DreamerDream:20210528122907p:plain

 (交換後の写真)

 

交換の方法はいろんなサイトで詳し〜く説明されていますので、あえてここでは記載しません。

 

Switchは流石にユーザー数が多いので交換部品もAmazonにいっぱい出ています。

素人でもネジと交換部品だけあれば比較的簡単にモジュール交換出来る構造になっています(推奨はしません)。

 

 

 

さて、僕の興味はこのコントローラーの内部構造です。

(新:左(交換品)、旧:右(純正))

f:id:DreamerDream:20210528122857p:plain

 

交換対象の旧部品を分解しました。

f:id:DreamerDream:20210528122924p:plain

分解してみると、なんと想像以上に簡素な作りでした。

分解前にイメージしていたものは、被膜抵抗式のポテンショメーターを2対使ったような構造でした。

 

<ポテンショメーターのイメージ>

 

実は、Switchのプロコントローラー↓

 

こちらには、イメージしていた通りのパーツが使われているようで、交換部品もこのようにしっかりした作りです。

 

「プロコンは操作性が良い」と言われる理由が解ります。

 

一方、本題のSwitch付属のジョイコンは良く言えば「コストをしっかり抑えた構造」です。

コントローラーの動きを感知するセンサーの動き↓
youtu.be

 

この端子に接触するようにフィルム基板が設置されています。

f:id:DreamerDream:20210528122954p:plain

端子の僅かな動きをフィルム基板に付着させた小さな被膜抵抗(黒色のL字の部分)の抵抗値として読み取っているようです。

f:id:DreamerDream:20210528122936p:plain

黒色の中に金色が見えますが、これが今回の故障の原因です。

被膜抵抗が端子の摩擦で削れ取れてしまっています(要するに使いすぎです)。

 

そこで、削れた部分を避けるように端子を動かせないか?こんな実験をしてみました。

被膜抵抗に接触する端子を広げてみました。

f:id:DreamerDream:20210528122945p:plain

 

結果

ダメでした。orzがんばったのにぃ・・・

 

 

こんな無駄な努力しなくても交換部品はamazonで安く出ているので素直に買って交換した方が安定して長持ちします。

 

これから「もしかしたら分解して中の部品ちょっと弄ったら直っちゃうんじゃないかな?」と僕のように考えている方にこのブログを残しておくことにします。

 

あと、このコントローラーの故障、単なる接触不良ならデコピンで直る場合もあるらしいです。

 

 

dreamerdream.hateblo.jp

 

 

 

1個45円の激安マイコン、PIC10F222を使って工作してみた 備忘録

電子工作でよく使われるマイコンにArduinoやPICがあります。

 

僕は普段ArduinoやRaspberryPiを好んで使っているのですが、多機能&高価なので単純な動作をさせるだけの工作には勿体ないものです。

マイコンに単純な動作をさせるには小さくて安いPICがオススメです。 

ということで、単純な用途でマイコンを使いたい今回、数年ぶりにPICを使って工作をしました。

大分忘れている記述がありましたので備忘録として残しておきます。

dreamerdream.hateblo.jp

 

今回使ったマイコンはこちら「PIC10F222」というもので、8ピンのDIPパッケージのもの(機能があるのは6ピンだけ)です。

f:id:DreamerDream:20210524092301p:plain

このマイコン、内部発振回路を内蔵しているのでオシレーターを繋がずとも上のような基板でモーターやLEDを制御出来ます。プログラムなのでタイマーIC555等を使うより遥かに単純な回路で小さく組め、より複雑な動作をさせることが出来るスグレモノなのです。

電源電圧も2.0V~5.5Vと広範囲なので乾電池2本(3V)〜3本(4.5V)で動作します。

8ビットのアナログ入力もついているので距離センサーやボリュームを繋げることも当然可能!というこのマイコンのお値段はなんと45円!(秋月電子)

Arduinoなんかと比べるとめちゃめちゃ安いです。

 

回路が小さくなると書きましたが、同じ機能でさらに小さい表面実装の米粒サイズのものもあります↓

15個 PIC10F222T-I/OT PIC10F222 10F222 SOT23-6 IC

これは流石にハンダ付けがしんどいので僕はDIPサイズで充分です。

<日本語データシート >

https://akizukidenshi.com/download/ds/microchip/PIC10F220_222_JP.pdf

 

 

何に使ったかというと、余っているモーターと組み合わせて・・・

f:id:DreamerDream:20210524092312p:plain

 

パナソニックのインターホン「アイホン」の時間延長マシンを作りました。

 

アイホン テレビドアホン ROCOワイド録画 電源直結式 録画機能付 スリムデザイン JRS-1AE-T

 

このインターホン(数世代前のバージョンですが)、外の様子を見ながら来客を待っていたい時などにモニターから外の様子を見ていると1分で切れてしまう(延長するには1分以内に再度モニタースイッチを押すとそこから1分延長)ので長時間外の様子を見ようと思うと何度もボタンを押さなくてはいけないのです。

面倒くさいことは機械にさせるのが得策ですよね。

 

ということで、完成したのがこちら↓

f:id:DreamerDream:20210524092330p:plain

電池3本が入る筐体は3Dプリンター製です。

ほぼ現場合わせで作ったので適当ですが^^;

f:id:DreamerDream:20210524092347p:plain

本当はインターホンの基板を開けてボタンの配線だけ弄りたかったのですが、インターホンの性質上改造中に来客があったり元を壊してしまうとしばらく困るので妥協して外付けにしました。

 

実際の動作の様子

youtu.be

 

備忘録として回路図とプログラムを残しておきます。 

回路

f:id:DreamerDream:20210524104458p:plain

単純な回路です。

モーターはDVDドライブのトレーの開閉に使われていた物で詳細不明、FETを使わずとも汎用トランジスタ1815で動いたのでノイズ対策だけしてOKとしました。

 

PICのプログラム環境は懐かしいWindowsXPにMPLAB IDE v8.92が入っていたのでそれで作りました。

 

プログラム

内容は単純にモーターを0.5秒動かしてそこから50秒待つ、以降繰り返す。

待ってる間は動作確認用として1秒周期で点滅させるというだけのものです。 

#include  <pic.h>#include  <pic.h>
/*****  コンフィギュレーションの設定  ********/

//file:///C:/Program%20Files/Microchip/xc8/v1.30/docs/chips/10f222.html#pragma config MCLRE = OFF, WDTE = OFF, IOSCFS = 4MHZ, CP = OFF, MCPU = OFF
//CPU4MHz設定(プログラム内delay関数用)

#define _XTAL_FREQ 4000000

 

/*GPIOの役割設定*/
//動作確認用点滅LED

#define Led GP0

//モーター制御

#define Motor GP1

//モーターOFF時(特に意味は無い)

#define Wait GP2

// GP3 = インプット専用(使わない)

 

/*グローバル変数宣言*/

//汎用変数i

unsigned char i = 0;

//カウンター用変数

unsigned char cnt_100ms =0;

 

/* initial */

void init_com(void){

  /*STATUS設定

  bit 7:ピン変化によるウェイクアップ(GP0, GP1, GP3) 0:電源投入時リセット 1:ピン変化リセット

  bit 6:Non

  bit 5:Non

  bit 4:タイムアウト 0 WDT 1電源投入

  bit 3:パワーダウン 0sleep命令 1電源投入

  bit 2:ゼロビット 0算術演算結果が0以外 1結果が0

  bit 1:デジットキャリー・ボロー 0キャリー発生なし、ボロー発生あり 1逆

  bit 0:キャリー 0 1*/

  STATUS =0b00000000;


  /**  OPTION設定 

  bit 7 :ピン変化によるウェイクアップGP0 GP1 GP3 0有効 1無効 

  bit 6 :弱プルアップ 0有効 1無効 

  bit 5 :タイマ0クロックソース 0内部 1T0CKIピン 

  bit 4 :タイマ0ソースエッジ 0 L->H 1 H->L 

  bit 3 :プリスケーラ0 タイマ0 1 WDT 

  bit 2-0 :プリスケーラレート選択 0 1    **/

  OPTION = 0b10000000;

 

  //アナログ入力設定(デジタル出力するにもデジタル入力設定が必要) 

  ADCON0 = 0b00000111; //0 Analog 1 digital

  //入出力ポートの設定 

  TRIS = 0b11111000;//出力:0 入力:1  (GP3は入力のみ)
  //ポートの初期化 

  GPIO = 0b00000000;
}

 

/* wait (0 - 255) *100m secound */

void delay_100ms(unsigned char cnt){

  for(cnt_100ms = 0 ;cnt_100ms < cnt; cnt_100ms++){

    __delay_ms(100);

  }

}

 

/* メイン */

void main(void){

  init_com();
  while( 1 ){
    Wait = 0;

    //モーターON

    Motor = 1;

    delay_100ms( 5 );

    //モーターOFF

    Motor = 0; 

    Wait = 1;
    for(i = 0; i < 100 ; i++){ //50s

      //LEDのHI/LOWを入れ替える

      Led = !Led;

      delay_100ms( 5 );

    }
  }
}

 

PICはArduinoと比べると初期設定やピンの機能は少しややこしいのですが、そこさえクリアすればArduinoより遥かに安く作品を小さく作り上げる事が出来るのが強みです。

python3でopenCVを使って2台のカメラ画像をゲットするために ラズパイでUSBカメラを2台認識しない問題を物理的に解決してみた

以前にapt-getを使ってopenCVをインストールしていましたが、これでインストールされるのはpython2系だそうです。 

dreamerdream.hateblo.jp

python2系のインストールコマンド

sudo apt-get install python-opencv

 

 

python3でカメラを使うにはpip3を使うそうです。

sudo pip3 install opencv-python

 

しかし、ソース上の

import cv2 

 

これだけでエラーが出ました。

エラー内容

ImportError: libcblas.so.3: cannot open shared object file: No such file or directory

 

ググるとこちらの記事がヒットしました。

rikoubou.hatenablog.com

 

こちらの記事の通り不足しているライブラリをインストールします。

sudo apt-get install libatlas-base-dev

 

上記の記事は他にもいろいろライブラリを入れていますが僕の環境の場合はこれだけでpython3でopenCVが使えるようになりました。

 

さて、問題はカメラの方です。

 

ls -la /dev/v4l/by-pathとlsusbコマンドでデバイスの確認

カメラ無接続

f:id:DreamerDream:20210423163328p:plain

カメラ1台接続

f:id:DreamerDream:20210423163338p:plain

カメラ2台接続

f:id:DreamerDream:20210423163354p:plain

 

デバイスが1つ増えるごとにvideoの番号が2つ増えています。

理屈はよく解りませんが、左右のカメラをopenCVで取得するには増えた番号の先頭である0と2をインデックス番号として

cap_L = cv2.VideoCapture(0)

cap_R = cv2.VideoCapture(2)

 

とすれば良いだけのようです。

 

しかし、これ起動ごとに左右入れ替わることは無いのだろうか?

 

と思って再起動すると・・・

f:id:DreamerDream:20210423164422p:plain

えええ???

2台目が認識されていません!!

 

テストで2台の画像を取得していたコードもエラー出現!

[ WARN:0] global /tmp/pip-wheel-qd18ncao/opencv-python/opencv/modules/videoio/src/cap_v4l.cpp (893) open VIDEOIO(V4L2:/dev/video2): can't open camera by index
Traceback (most recent call last):
File "camera.py", line 60, in <module>
caps()
File "camera.py", line 46, in caps
cv2.imwrite(path_R, frame_R) # ファイル保存
cv2.error: OpenCV(4.5.1) /tmp/pip-wheel-qd18ncao/opencv-python/opencv/modules/imgcodecs/src/loadsave.cpp:753: error: (-215:Assertion failed) !_img.empty() in function 'imwrite'

画像が無いので保存出来ませんよというエラーです。 

 

ははーん、どうやらUSBの接続に問題があるようです。

 

そこで、こちらの記事を参考にソフトウェア的にUSBの電源を一度OFFにしてONにすることでUSB接続の情報をリセットが出来るかも?と試してみました。 

vogel.at.webry.info

 

スクリプトも書きました。

### usb_rebind.py ###

#!/usr/bin/python
#coding:utf-8

import subprocess
import time

def off():
  subprocess.call('sudo sh -c "echo -n \"1-1\" > /sys/bus/usb/drivers/usb/unbind"',shell=True )

def on():
  subprocess.call('sudo sh -c "echo -n \"1-1\" > /sys/bus/usb/drivers/usb/bind"',shell=True )

if __name__=='__main__': # if script
  off()
  time.sleep(3)
  on()

 

結果、ダメでした orz...。

試しにUSBハブに2台繋いで同時に接続してみても認識しません。

 

別々で繋ぐと認識出来ます。おそらくカメラの相性ですね。

・・・困りました。(ーー;ムムム。。。

 

 

ということで、物理的に切断&接続するという暴挙に出ます。

f:id:DreamerDream:20210427121108p:plain

USBケーブルのここを切り、手持ちのFETでGNDに落とします。(推奨しません)

 

回路

f:id:DreamerDream:20210427123317p:plain

FETはNchパワーMOSFET 2SK4017(Q) (60V5A)を使用しました。

 

 

この回路の状態で試しにマウスを接続して起動させると、なんと信号線をGNDとしてマウスが普通に使えてしまいました orzやっぱりか。。。

しかし、純粋にUSBカットは出来ないようですが、カメラを繋いでON-OFF-ONと繰り返すと電圧差の加減なのかカメラのOFF→ONは出来ました。(これもカメラの相性があるかもしれません。)

 

スクリプトには

time.sleep(3)
on()
time.sleep(1)
off()
time.sleep(1)
on()
print('USB-3 RESET')
while True:
  time.sleep(60)

と書いてサービスに登録、ラズパイ起動3秒後にon-off-onとさせます。

GPIOの制御は基本のLチカですので割愛します。

dreamerdream.hateblo.jp

 

 

これでやっとカメラ2台を認識するようになりました。

f:id:DreamerDream:20210423163354p:plain

 

信号線にGNDが流れてしまうのでラズパイの回路には優しくないと思うので推奨はしませんが、今回はこんな方法で認識しましたという報告でした。

 

以上です。

 

<参考> 

dev.classmethod.jp

 

qiita.com

www.fixes.pub

kampa.me