鯖の構成見直し

昨日勢い余っておニューなサーバー構成検討と称して構成例を考えた。

ケースにRAIJINTEKのSTYXを選んだが、今日実物を見に行ったら気が変わった。

METISをほぼそのまま相似形に大きくしたのがSTYXだと思っていたが、上面に通気口が追加されているのであった。(側面にストレージスペースが追加されてるとかもあったけど、上面通気口と比べれば些事)

 

あまり掃除をしない人間なので(掃除すればいいんだけど)、上面の通気口はあまりうれしくない。ホコリが中に入る。上面から排気するようケースファンを追加すればある程度防げるような気もするけど、常時稼働を目指すので騒音源はなるたけ少なくしておきたい。件の通気口は公式サイトによれば240mmのラジエータをサポートするスペースのようなので、要は120mmファンを2つ装備しないと塞げない。

 

それから、寸法は数字としてはわかっていたけど、やっぱり実物で見るとMETISがとっても小さいしそれと比べるとSTYXは思ったより大きい。

 

つーわけで、METISに戻します

 

それに伴ってマザーボードをmini-ITXのものにしなければならないのだけど、価格.comの検索条件をSocketFM2+だけにするのではなく、SocketFM2/FM2+にすると多少検索ヒット件数が増える。

無線通信機能を持つものが殆どだが(8件中7件)、正直不要である。801.11ac対応するらしいけど、我が家の無線LANアクセスポイントはNECの普通の(ふるい)ホームルータであるので対応しない。そんな状況でサーバ用途で使うのはちょっとねぇ…というわけで不要。

無線通信をサポートしないのはBIOSTARのHi-Fi A88ZNのみ。BIOSTARマザーはむか〜し(恐らく現サーバ機より2世代前に)使ったのみで、しかも全く記憶に残っていない…今までずっと生きているという意味では、きっと確かなものがあるのであろうが、他メーカーより勢いがあるとは言いにくい状況という印象。

つーわけで無線は取り敢えず置いとくことにして、最近ずっと選んでいるASRockニキ…と思って、A88M-ITX/ac R2.0にしてみようかと。値段は9k程度なので、少しの増額分はSTYX→METISの減額分で賄ってなおお釣りが返ってくる。普通に全体予算が安くなった。

 

構成を再度示すとこんな感じ。右端にTSUKUMOないしAmazonでの値段を付している。

CPU : AMD A8-7670K (9686JPY)
M/B : ASRock A88M-ITX/ac R2.0 (9158JPY)
RAM : Crucial W3U1600CM-4G (6667JPY)
CAS : RAIJINTEK METIS (5280JPY)
PSU : KRPW-SXP400W/90+ (7084JPY)
SSD : Intel 540s SSDSC2KW180H6X1 (8154JPY)

さり気なく電源をFSPから玄人志向に変えました、ケースが小さくなったのでスペースが切実な問題となる。当然プラグインタイプ(セミだけど)。

総計は46029円。昨日の構成では48231円だったので、2kとちょっと安くなっている。より揃えやすくなったね、やったねたえち(ry

 

ケースだけ先に買っちゃおうかな、引っ込みつかなくなればちゃんと行動するでしょ

おニューなサーバー構成検討

現在の自宅鯖、とてもひどい事になっている。画面が一切出力されない(恐らく死んだ)。画面が出力されないが、それ以外はどうも生きているようなので、ギリギリ鯖として使えている…という状況。

さすがにこのまま使い続けるのは心がキツいし、10年も頑張っていただいたマシン、そろそろ引退させてあげたい(ただいきなり死ぬのが怖いだけ)。

 

というわけで、新しい構成を考えた……の前に、現在のものを主要なとこだけ。

CPU : Intel Pentium DualCore E5300
M/B : GIGABYTE GA-E7AUM-DS2H
RAM : 4GBx2(メーカーとか何も覚えてません)
HDD : 640GBくらい

10年くらい前に組んだので、ふるい。

 

さて、新構成はこんな感じ。

CPU : AMD A8-7670K
M/B : ASUS A88XM-A/USB3.1
RAM : Crucial W3U1600CM-4G
CAS : RAIJINTEK STYX
PSU : FSP AURUM S 400 AS-400
SSD : Intel 540s SSDSC2KW180H6X1

コストはAmazon価格で計5万円を切る。2月9日時点で48231円らしい。どれも在庫あり。

 

ほんとはRyzenが来てから考えたかったけど、構成考える欲求を抑えられなかった(金が入ったら即座に購入できる)(金が入るとは言ってない)

そんなに予算が無いのでCPUはIntelでなくAMDにしましょうっていうのは最初から考えていたが、もともとはケースにRAIJINTEKのMETISを使って組みたかった。これとてもコンパクトで6000円程度の手頃なmini-ITXケース。ケース内の向きが面白い、電源がスポッと立っててマザーは逆さ(詳しくは画像検索してください)

ただ、そんなに手頃なmini-ITXマザーが見当たらなくて、FM2+なmini-ITXマザーが価格.comに1件しか料金登録が無い、あまりにもひどい…

しょうがないので、METISの姉妹製品であるSTYXに方針変更。これはMETISに+3000円程度して、micro-ATXが使えるって感じ(デザインと内部のパーツ向きは同じっぽい)。

 

CPUについては、詳細な検討ではないけど、前のが前のだけに、(cpubenchmark.netのスコアによると)15475015と十分な伸び(ちょっと前までメインで使っていたCore i7 870が5424らしいので十分)

メモリは8GBもあれば十分かなと思うし、不足しそうだったら追加すればいいかなとてきとうに思っている。マザーにはスロット4本あるし

 

マザー選びはいつも困るんだけど、大抵は値段で決める(今までそれでハズレを引いたことがないので)

オーディオは基板上で分離してるやで、と公式サイトではアピールしてるけど、実際あんまこだわらないし、鯖だしなぁ…と思ったりもする。気分が乗ったらアニソン垂れ流しシステムでも作ろうかな?

ネットワークはいつもの蟹さんが載ってるよう(RTL8111H)なのだが、一先ずはこれをそのまま使おうかな

 

電源も実はいつも困っている…が、そんなに電力必要じゃないので上限400W、一応常時稼働なので80PLUSはSilver以上で検索したら、玄人志向のKRPW-SX400W/90+, KRPW-SXP400W/90+か、FSPのAURUM S 400 AS-400しか出てこなかった。玄人志向の方はSFX電源で、後者は前者のプラグイン版っぽい。FSPのはATX電源。

FSPの電源は6900円なのに対して、玄人志向のプラグイン版が7000円なので、プラグインに惹かれてこっちを選んでもいいかなっていう気もする。ただ、ケースをMETISじゃなくてしたので、別にスペース気にしなくても良さそう…というわけでめっちゃケーブル余らせてもいいかな〜とは思う(アクリルで中身見えるやつなのでスッキリさせるに越したことはないかな)

 

ストレージはもうてきとうに。取り敢えずIntel選んどけばいいじゃろってくらい。マザーが対応してたとしても(してないけど)、鯖機にM.2はつけなくていいかな、などと思いこんでいるので普通の。容量はお財布と相談で180GBにしておいた。

そんなに大容量が必要なわけじゃない気がするので取り敢えずシステム用SSDだけでいいけど、ダメそうになったらてきとうにHDD1つ追加する心積もり。500GBくらいなら安く手に入るでしょ

 

さて、OSについては、今までUbuntuDesktop(なぜServerではないのか…)使ってたけど、それなりに慣れてきたしということでArchLinuxでもいいかなと思っている。鯖として使うには不安定なのではとも言うけど、個人宅内鯖でとやかく言うことでもない。

そんで、その上にsystemd-nspawnでコンテナ立てて、てきとうにサーバソフトウェア起こせばそれでいいかな?と。どうしてもUbuntuほしければコンテナの上に立てれば良いので。

 

 

以上、実際の構築は棚の上に上げておいて、てきとうに検討だけしました。お金が用意出来たら組むぞ〜〜

 

LAN内にいるIPアドレスを一覧したい nmap,arp-scan

DHCPで繋いだ時のIPアドレスがわからなくてこまる事がある。例えば何もいじってない状態の玄箱にtelnetしたいとか。そういえば玄箱全然いじってないな。

という訳でLANの中にいるIPアドレスを調べる。

nmapは-sPとか-PRとかつけて目的ネットワークを指定すればおk

sudoつけないと色々面倒なお話があるのだが、ネットワークのお話をちゃんと勉強しないとわからないっぽいので後日。(sudoつけなくても使えるが機能が制限される)

 

次、arp-scanは-I(–interface)でインターフェイスを指定して、-l(–localnet)オプション付ける

localnetオプションは検索対象をローカルの全てのアドレスにする。インターフェイスのアドレスが192.168.0.3/24とかだったりすると、192.168.0.0〜192.168.0.255を探索するようだ

こっちはそもそもsudoつけないと怒られる(パケットを読み書きするのにroot privilegeが必要)

 

$ nmap -sP 192.168.0.0/24
$ sudo nmap -PR 192.168.0.0/24  # ポートスキャンやってくれる
$ sudo arp-scan -I wlp2s0 -l

dnsmasqで内向きDNS

今更なネタではあるような気がするけど、dnsmasqで内向きDNSを立てた。

以前、ArchLinuxのリポジトリミラーをローカルに立てるという事で、ローカルにミラーを立てたのは良いけれど、家にいるときはローカルミラー、外にいるときは他のミラー…というように接続先を変えるのが面倒くさい。

実はネットワークに接続するたびに毎度毎度mirrorlistを手作業でいじっていたのだ。アホ。

これ自動化する手があるのかもしれないけど、それよりも、ドメイン登録して外からローカルミラーにアクセス出来るようにして、自宅からは内向きDNSで解決するようにして、mirrorlistにはいつも同じドメイン名書いておけばよいのでは?という結論にいたった。しょーもな。

という訳でそういうお話。

 

dnsmasqは/etc/hostsをもとに名前解決してくれるDNSサーバとして使う事が出来る(BINDみたいに面倒な設定書かずに済んで楽ちんなのだ)

 

 

やることをまとめると、

・それらしいドメイン名で自宅外から自宅内のマシンにアクセス出来る

・自宅内でも同じドメイン名でローカルマシンにアクセス出来る

 

今回は、repo.hoge.comを192.168.0.3とかにあててみようと思う。

 

まずはdnsmasqを導入する。

$ sudo pacman -S dnsmasq

何も考える必要ないっすね。で、設定をいじる。/etc/dnsmasq.confにいる。

domain-needed
bogus-priv
local=/hoge.com/
no-dhcp-interface=enp6s0
expand-hosts
domain=hoge.com

次、/etc/hosts

$ cat /etc/hosts
127.0.0.1 localhost.localdomain localhost
::1 localhost.localdomain localhost
192.168.0.3 repo.hoge.com

サーバの設定はおしまいなので起動設定(と起動)

$ sudo systemctl enable dnsmasq
$ sudo systemctl start dnsmasq

気になるようだったらサーバでrepo.hoge.comにpingとかしましょう

/etc/hostsを設定した時点でサーバ内では名前解決出来るけど、ローカルネットワークの他のマシンからは名前解決出来ない。DNSにサーバを指定すればともかく、それをしたら他のネットワークに参加した時にまた対応せにゃならんでしょう(プロファイル作ってわけるってのもあるけど、手作業が面倒なのが根本なのでなしの方向で)

つー訳で、ルータから特定ドメインの名前解決リクエストだけサーバに飛ばすように設定する(たぶん)。我が家のルータはAterm WR8370Nなので、他の機種他のメーカーは知りません(

設定Web→詳細設定→DNSルーティング設定にルーティングエントリとして追加する

宛先ドメイン:repo.hoge.com
ゲートウェイ:192.168.0.3
プライマリDNS:192.168.0.3

あとは設定を保存して動作チェックだ。

 

最終的な状況は、

自宅LAN外からアクセス→おなまえどっとこむのDNSを使って名前解決→通常のサーバのようにポートマッピングでサーバへ接続

自宅LAN内からアクセス→LAN内メインDNSサーバたるルータへ要求→ルータは設定されたドメインなので192.168.0.3へ転送→192.168.0.3のdnsmasqが解決してくれる

という感じかしら?

 

これ、別にリポジトリミラーの話に限る必要は無くて、自宅鯖とかに普通に使えるんすよね…

自宅にあるマシンはどれも手作業でhostsいじってたけど、これからはこれ使って楽ちん設定だー。

特定コマンドが含まれているパッケージを探す

ArchLinuxって最小限のインストール構成だと(最小限なので当然なんだけど)使いにくいレベルで何も入ってない。

そこから好きなもの、必要なものだけに絞ってインストールしていけるので、大変そういう意味では良いんだけど、まともに環境構築するつもりはなくて、とにかく実験環境とか遊び環境として一つ欲しいときに、「あのコマンドだけ欲しい」とかあるんすよ

最近研究室に新しいサーバ機が届きまして、早速諸々の構築をしていきたいんだけど、教授からは「Windows Serverにしような」と言われてしまい、しかしそのインストールメディアは先生が持っていて、更に言うとストレージも実は用意してないので、やっぱり何も出来ない状況なのだ…

とは言え、こんな格好のおもちゃ、放置しておくのは勿体無いよねって事で、USBメモリにOSをインストールしてそこから起動して色々遊べばいいじゃん〜と。

要はまともに環境構築する気が無い環境で、アレ欲しいコレ欲しいって単発で欲しくなったときに、具体的にどのパッケージをインストールすれば良いのかを探す。

 

今回欲しかったのはifconfig。NICの名前とかIPアドレスとか知りたいとふと思ったときに無意識に打ち込んじゃうけれど、これ最初は入ってないんでした……

pacmanにオプションQoをつけて目的バイナリを探してきてねってお願いすると、パッケージ名出してくれます。

 

$ which ifconfig
/usr/bin/ifconfig
$ pacman -Qo /usr/bin/ifconfig
/usr/bin/ifconfig は net-tools 1.60.20160710git-1 によって保有されています

2行にわたったり入力したりめんどいので以下みたいなノリで短縮も可

$ which ifconfig | pacman -Qo -

aliasなコマンド(lsなんかはls –color=autoになっている場合をよく見る)の場合には一度unaliasする以外方法見つかりませんでした(まがお)

関数の引数として関数をとる

C++なら関数オブジェクト使えとかいう記述をどこかで見かけたんだけど、結局よくわからなかったので関数ポインタを使う事にした。

引数の型 (*関数ポインタ名)(その関数がとる引数の型)

という形で宣言して使う。

例えばintで1つ引数をとって、5足したものを返してくれる関数を考えてみる。

int calc(int in){
return in+5;
}

int main(){
int (*fp)(int);
fp = calc;
fp(2)    // 7が返ってくる
return 0;
}

細かいアレはともかくとして、fpが関数ポインタ。こういう使い方だと今のとこあんま面白くないけど、関数ポインタを使えば関数の引数に関数を使える。

与えられた関数から返ってきた値の正負を判定する関数pmを考える。

int calc(int in){
return in+5;
}

bool pm(int (*fp)(int), int in){
if(fp(in)<0){
return false;
}else{
return true;
}
}

int main(){
pm(calc, -6)    //false
pm(calc, 3)    //true
return 0;
}

使いどころは、計算の一部分を利用者から与えてもらって、それを使って全体の計算をやるって場面。(ていうかそういう場面があったのでこうやって書きました)

具体的に言うと、数値解析のときにつかうテクニックがあるんだけど、これを毎度書いてるとウザいので、オレオレライブラリにしてやろうという感じ。テクニックのアルゴリズム自体はライブラリ側で全部書いておいて、利用者は目的関数の定義だけしてあとはそれを放り込むだけ〜というやつ。

ぶっちゃけこういう内容1年くらい前にやるべきみたいな雰囲気はある(今年度何した?に答えたくない)

あけましておめでとうございます(今更)

今更なんですが、あけましておめでとうございます。

年末のまとめ記事とか年始の目標記事とかそこかしこで見かけるので、てきとうにマネしてみようかと思いました。

まぁ、てきとうに何かを書きます

 

今年の目標(いまのとこ)
・シュウカツ
・学業なんとか
・放置しているプログラムを発掘してちゃんとしようかなとか
・自宅サーバのReplace
・ノートPCの新調

 

就活は言わずもがななんですよね。自分今大学院の1年生なんですけど(これから2年生になる)、進路キメないとっていう…

学業も、そろそろ本腰入れて研究進めないと何もやらないまま終わってしまう…アカン…………

 

で、放置しているプログラム。ぱっと思いつくのは2つ。

1つはAskMonaのクライアント(もな茶漬け)。タブ機能つけようとして色々いじってたら、過去自分が書いたコードが汚すぎてフルスクラッチで作り直す事を決意した…のはいいけど作業を何もやってないんですよね。今まで書いたものを全部無かったことにする訳だし勇気が…

2つめはツムツムの自動プレイヤー。ツムツムはその他のソシャゲと同じで、プレイにスタミナみたいなもの(ハート)が必要になる。で、このハートをLINE友達と相互に送り合う事が出来るので、時間で回復するのとは別に、ハートを得ることが出来る。一時期ハート交換グループに所属していた事があって、そのときに得たハートが沢山残っている(1ヶ月間以上連続プレイ出来る分量)。
で、ツムツムっていうゲーム、上手にプレイする事もそうなんだけど、とにかく沢山プレイしてレベルを上げていかないとスコアが上がらない。
つー訳でこれ自動化出来ればだいぶ捗るんじゃね〜〜〜〜?と思って1年ちょいくらい前にOpenCVでなんやかややってたんだけど、その当時まだプログラミングに全然慣れていなかったのでクソみたいなコードを書き連ねて、そのままお蔵入りになってしまった…
多少慣れてきたはずなので、今ちゃんとやりたいところ。

実は他にもあると言えばあるんだけど、面白そうかな〜やりたいな〜って思ってるのは取り敢えずこの2つ。

これとは別に、友達と「こんなシステム(サービス)あったら便利だよな〜」ってお話をして、設計とかやってる最中なのがあるんですが、これはもう用途がニッチなのであんまりおおっぴらにはしないかなーと。

 

つぎ。自宅サーバのReplace

今使ってる鯖は、もう十年近くもまえに組んだデスクトップPCの流用なので、相当キツい。オンボードのグラフィック機能が死んで画面表示が出来ない状況になっていて、結構ギリギリの状態で生きている。

AMDで組めば安くそれなりのものが出来るんじゃないかと(Ryzen期待)思っている。消費電力も抑えられればそりゃ嬉しいし、性能が上がれば仮想化してサーバを分けたりしたい。(今は自宅鯖とは別にNASとして別マシンを稼働させてる)

Ryzenの続報とか実際のベンチとか、情報が出てくるまで待つ心積もり。

 

さいご、ノートPCの新調

今使ってるのは大学入学時に購入したVAIO(S series)。載ってるのはCore i5 480Mで、もう世代的にキツい。それから、ずっと持ち歩いているからか、普通に角とか破損してるし、液晶周りのベゼルとかももうバキッと行きそうなレベルで亀裂が入っている。あと重い(物理的に)

という訳で新調を考えている。

候補はMacBook Pro Late 2016かDell XPS13 9360あたりかな。他にもあるかも?

・US配列に出来る事
->JIS配列本当にやめてほしい
・トラックパッドのスイッチが扱いやすい(出来れば独立して欲しいけど妥協可)
->Surface Pro 4のトラックパッドとか最悪
・Linuxうごく
->某Lenovoのヨガった奴みたいな事してくれないでくれると助かる(修正BIOS出てるらしいけど怖いジャーン?)

あたりを気にしている。モニタサイズは13インチくらいであれば良いけど、本体重量とか厚みとか電池持ちとかはあまり気にしてません。どうせ今使ってる奴より状態が悪くなる事はきっとないのだ、古いし劣化してるしなので。

なんでMacBookが入り込んでいるのかというと、どうせ新しくするなら、今まで触れたことのない新しい世界に飛び込んでみるのもいいんじゃないかなと思っただけ。ちょうどAppleレートも効いてるし、24回ローン金利0%キャンペーンもやってるし。あとバタフライキーボード割と嫌いじゃないです。

Linuxは現状動かないみたいだけど、macOSってUNIXベースなんでしょ?まぁなんとかなるっしょ()みたいな感じでナメきっている。で暫くしてLinux動くようになりそうだったら、ArchLinux突っ込んでしまえと思っている感じ。

で、まぁ、候補がいくつあろうが、どれにしようかなと悩もうが、結局お金が無いのでどうしようも無いんですけどね。

 

 

また何か思いついたらまた新しい事やると思います。いきあたりば(ま)ったり。

bashでゼロパディングする手法2つ

連番を頭につけたファイル群を取り扱う時、並び順を考えるとゼロパディングしておきたくなる。

例えばソートしたときに、

1
10
11
~略~
2
20
21
~略~

みたいな事されると、理想の並び順ではない。理想は勿論、

1
2
~略~
10
11
~略~

というような状況。最大桁数をカバー出来る桁数でゼロパディングしておけばこういう事故も起こらないはず…

という訳でゼロパディングする手法2つ。

話を簡単にするために8~12の5つを作ってみる。

 

その1

$ for ((i=8; i<13; i++));do
str=00$i;
str=${str:(-3)};
echo $str;
done
008
009
010
011
012

2行目では008~0012までを単純に作る。後にこれを${str:(-3)}で、末尾から3文字だけ取り出す事によってゼロパディングをする。

 

その2

$ for ((i=8; i<13; i++));do
str=`printf "%03d" ${i}`;
echo $str;
done
008
009
010
011
012

C言語のprintfでゼロパディングするときと同じ感覚。

 

 

その1の方がすっきりと言えばすっきりだけど、2行にまたがるのが微妙な気持ち(1行にまとめる方法は勿論ありそうだけど)

その2なら新たな記法を覚えなくて済むし簡単に1行にまとまるから良い…けれどbashで、という気持ちのくせになぁ、みたいな…そもそもforの中身がCスタイルなんですけど。

マルチプロセスとマルチスレッドの区別

C++でマルチスレッドにプログラムを書いた事はあったので、並列動作の基本はOKだぜ!と思っていた。

ネットで拾ったコードを特に意識せずいじっていたらどうしてもうまくいかなくて、途中で気づいた。これマルチスレッドじゃなくてマルチプロセスだ。

 

というわけで区別しましょう。

 

まずはマルチプロセス

まずはマルチプロセス。fork()関数で子プロセスを作るんだけど、これ、状態を全部コピーした上で子プロセスが動く。例えば以下のようなコード。

#include <iostream>
#include <unistd.h>
using namespace std;
int i;

int main(){
 i=0;
 cout<<"process fork test"<<endl;
 pid_t pid;
 if((pid = fork()) == 0){
 cout<<"this is child"<<endl;
 sleep(10);
 cout<<"child dead"<<endl;
 cout<<"i:"<<i<<endl;
 }else{
 sleep(5);
 cout<<"this is parent"<<endl;
 i++;
 }
 return 0;
}

fork()は、プロセスをフォークしてくれる関数だが、この戻り値をうまく使う。戻り値は、当人が(?)子プロセスの場合には0、親プロセスの場合には子プロセスのPIDを与える。

これを実行すると、

[tea@teaarch]$ ./a.out
process fork test
this is child
this is parent
[tea@teaarch]$ child dead
i:0

のようになる。

実行の順番は、

1. i=0に初期化
2. フォーク
3. 5秒経過
4. 親プロセスが自己紹介してi++;して終了
5. 5秒経過
6. 子プロセスが自己紹介してiの中身を出力して終了

単純に考えると、6.では1を出力しそうなもんだが、別プロセスであり、(マルチスレッドの時のように)共有していないので、インクリメントされる前のiを子プロセスは持っており、インクリメントされないまま出力を迎える。

それから、親プロセスが終了した時点で、制御が帰ってくるみたい。(親プロセスが終了しても子プロセスは生き残る)

 

それからマルチスレッド

こちらはプロセスの中で処理スレッドを増やすものなので、メモリ空間は共有。例えば以下みたいなコード。

#include <iostream>
#include <thread>
#include <unistd.h>
using namespace std;

int i;

void sub_thread(){
 cout<<"[s]this is sub thread"<<endl;
 sleep(3);
 cout<<"[s]i:"<<i<<endl;
 sleep(3);
 cout<<"[s]i:"<<i<<endl;
}

int main(){
 i=0;
 cout<<"multi thread test"<<endl;
 thread t(sub_thread);
 t.detach();
 cout<<"[m]sleep..."<<endl;
 sleep(5);
 cout<<"[m]increment"<<endl;
 i++;
 cout<<"[m]sleep..."<<endl;
 sleep(5);
 return 0;
}

コンパイル時には忘れずライブラリくっつけておく。g++ ./thread.cpp -lpthreadみたいな感じ。実行すると、

[tea@teaarch]$ ./a.out
multi thread test
[m]sleep…
[s]this is sub thread
[s]i:0
[m]increment
[m]sleep…
[s]i:1

動作は、

1. i=0に初期化
2. サブのスレッドt作成(中身はsubthread()が動作する)
3. detach()でスレッドtの管理を放棄(スレッドtが終了するまで待つのは.join())
4. 3秒経過
5. サブスレッドがiの中身表示(0)
6. 2秒経過
7. メインスレッドがiをインクリメント
8. 1秒経過
9. サブスレッドがiの中身表示(1)
10. 4秒経過
11. メインスレッドが最後のスリープをして終了

これ、最後のスリープをしないと、メインスレッドが5秒経過後インクリメントした直後にプロセスが終了する。サブスレッドは6秒たたないと2回めの表示をしないので、つまり、1回目の表示しか実行されない。

 

まとめ

マルチプロセス:fork()とかでうまくやる。メモリの状況はコピーされ、共有されない。親プロセスが終了しても子プロセスは生き残る。親子プロセスで何かやりとりしたければプロセス間通信の手を考える必要がある?(名前付きパイプとか?)

マルチスレッド:threadでうまくやる。メモリの状況は共有される。メインスレッドが終了すると派生した方のスレッドも終了する。スレッド間のやり取り自体は難しくないが、タイミングの制御やロックなど考えないと死ぬ(よくあるマルチスレッドの注意点)

PDFを結合する(pdftk)

PDF結合?取り敢えずImageMagickやろwwwwwwとか思ってconvertバシバシ叩いてたんだけど、圧倒的メモリ不足で全然終わらない(RAM4GB+Swap4GBを全部食い潰していた)

なんやこれと思って暫く悩んでいたんだけど、どうしようもないのでぐぐってみたら、一発目から「pdftk使っとけよw」って煽られたのでそういうことだ。(´・ω・`)

 

pdftk、分割しか出来ないと勝手に思い込んでいた

pdftk [INPUT FILES] cat output [OUTPUT FILE]

処理もサクッと終わるとメモリも全然食わない

わからなければ素直にぐぐりましょう。