Posts for: #Security

暗号化と復号化を実装してみる

不定期に寝て7時半に起きた。起きてからシャワー浴びたらしゃんとした。昨日と同様に昼間働いて、ホテルに戻ってきて2-3時間寝てから夜に2-3時間かけて次のコードを書いた。

go での暗号化/復号化

ある機密情報を扱うので暗号化して普通には「みえない」ようにしたい。まったくわからないのでググったら次の記事がみつかった。

まずはこの記事にあるサンプルコードを動かしてみながら内容を理解する。暗号技術そのものは理解できないが、コードの振る舞いそのものは動かしながら理解できる。その後、いろいろ調べているとこのサンプルコードの大半は crypto/cipher パッケージにあるサンプルコードと同じであることに気づく。標準ライブラリのドキュメントでは iv (initialization vector) を暗号化対象の文字列の一部を切り取って生成している。iv は一意である必要はあるが、セキュアでなくてもよいとある。よくあるやり方とあるのでサンプルコードをみながら同じように実装した。

// The IV needs to be unique, but not secure. Therefore it's common to
// include it at the beginning of the ciphertext.

最終的な暗号化と復号化のコードは次になった。標準ライブラリにあるサンプルコードと基本的には同じ。

func Encrypt(secret string, plainText []byte) ([]byte, error) {
	block, err := aes.NewCipher([]byte(secret))
	if err != nil {
		return nil, fmt.Errorf("failed to create chiper: %w", err)
	}
	cipherText := make([]byte, aes.BlockSize+len(plainText))
	iv := cipherText[:aes.BlockSize]
	if _, err := io.ReadFull(rand.Reader, iv); err != nil {
		return nil, fmt.Errorf("failed to read for iv: %w", err)
	}
	stream := cipher.NewCFBEncrypter(block, iv)
	stream.XORKeyStream(cipherText[aes.BlockSize:], plainText)

	buf := make([]byte, base64.StdEncoding.EncodedLen(len(cipherText)))
	base64.StdEncoding.Encode(buf, cipherText)
	return buf, nil
}
func Decrypt(secret string, text []byte) ([]byte, error) {
	block, err := aes.NewCipher([]byte(secret))
	if err != nil {
		return nil, fmt.Errorf("failed to create chiper: %w", err)
	}

	dbuf := make([]byte, len(text))
	n, err := base64.StdEncoding.Decode(dbuf, text)
	if err != nil {
		return nil, fmt.Errorf("failed to create chiper: %w", err)
	}
	cipherText := dbuf[:n]

	if len(cipherText) < aes.BlockSize {
		return nil, fmt.Errorf("ciphertext is too short: %d", len(cipherText))
	}
	iv := cipherText[:aes.BlockSize]
	cipherText = cipherText[aes.BlockSize:]
	stream := cipher.NewCFBDecrypter(block, iv)
	// XORKeyStream can work in-place if the two arguments are the same.
	stream.XORKeyStream(cipherText, cipherText)
	return cipherText, nil
}

cookie の secure 属性と localhost

0時に寝て6時半に起きて7時半に起きて9時過ぎに起きた。普通は明け方に2度寝して起きるのになぜか3度寝して寝坊した。慌てて準備してオフィス行って業務開始が9時半をまわってしまった。年に1回ぐらい意味なく寝坊することもある。こういうことがあるから他人がなにか意図しない失敗しても寛容になれる。

以前たまたま Meety脆弱性 2022-11 をみたときに認証 cookie に secure 属性が使われていないという指摘をみかけた。http でログインするときに cookie にセッション情報を保存してしまうと、平文でセッション情報が流れてしまうのでセキュリティ的によくない。具体的な攻撃方法としては wifi の通信をパケットキャプチャするとか、ルーター (カフェの無料 wifi とか) で中間者攻撃 (man in the middle) などのセキュリティ上の懸念がある。その対策としては cookie の secure 属性を付けておくと、http のときはセッション情報をブラウザに保存しなくなるのでログインできなくなる代わりにそういった攻撃から守れるようになる。フロントエンドのセキュリティのお作法みたいなものにみえたので覚えていた。

ちょうど管理画面のログイン機能をメンバーに実装してもらったところなのでその対応をしているかどうかをメンバーに確認していた。メンバーもその認識はもっていて環境変数の設定で切り替えられるように実装していた。テスト環境にデプロイするときにその設定を有効にしてもらって、私が意図した振る舞いをしているかどうか、テスト環境にアクセスして検証していた。しかし、secure 属性が付いていることは確認したものの、http でもセッション情報がブラウザに保存されていて、あれー?って感じで検証していた。メンバーは保存されないという。

localhost は例外

ブラウザによっては localhost だと httpsの要件が無視されるとのことでした。

CookieのSameSite属性とSecure属性について

この記事によると localhost だと適用外になるブラウザがあるんだと気付いた。たまたま私が ssh の port-forwarding 経由でテスト環境にアクセスしていたので localhost 経由のアクセスになっていた。これは開発時は http でも動くようにすることで環境変数で切り替えるといった、それ自体がセキュリティインシデントになり得る設定をもたないようにするための、ブラウザベンダーの配慮だろう。chrome はそういう振る舞いをしていることを私は確認できた。

v-html は使わなくてもよい

0時に寝て7時に起きた。また日曜日は寝てた。

任意のカラムの書き換え

v-data-table の、あるセルが複雑なデータをもっていて、単純にその値を表示するのではなく、一定の構造化やレイアウトを調整した状態で表示したい。セル内の構造を書き換える方法を私は知らなかったので v-html という api を使って書き換えればよいのだと思った。しかし、これは間違いだった。間違いの訂正は翌日にやるとして仮に v-html を使うとしても xss の懸念があるのでスクリプトをエスケープしてあげないといけない。Sanitize v-html #6333 でも議論されていて vue3 はデフォルトでエスケープする仕組みが入るのかな?vue2 だと sanitize-html を使って次のようにラップすればいいと書いてあった。実際に動かしてみるとスクリプトを実行できたので v-html は危険だというのはわかった。

<div v-html="$sanitize(value)" />

この仕組みを作って pr でレビューしてもらっていたら、カラムの構造を書き換えたいだけなら slots を使えば普通にできると教えてもらった。また明日へ。

jvm の脆弱性対応

23時に寝て3時に起きて5時に起きて7時に起きた。なんか調子が微妙。

jvm の脆弱性対応

少し前だけど、jvm のセキュリティアナウンスがあった。

java 11 向けの docker イメージのビルドはあまり緊急度が高くなかったせいか、17よりは優先度が低かったようにみえる。docker イメージビルドの作業状況は次の issue で管理されている。

これまで adoptopenjdk/openjdk11:alpine-jre という docker イメージを使っていた。Transition to Eclipse - An Update によると、Eclipse Temurin という組織が管理する Adoptium というプロジェクトに移管されたらしい。この機会に docker イメージも eclipse-temurin:11-jre-alpine に移行した。

お花見の場所探し

0時に寝て5時過ぎに起きた。

spring framework の脆弱性対応

起きてタイムライン眺めてたら spring framework の脆弱性の公式アナウンスが出ていたのですぐに準備してオフィス行って7時前から脆弱性対応の作業をしてた。

大学の研究室にいた頃、root staff と呼ばれるシステム管理者をやっていた。研究室のネットワークをすべて freebsd で自分たちで構築していたので os の脆弱性が公表されると研究室のすべての os のパッチ適用をやっていた。具体的にはパッチの当たった kernel をビルドして再起動するといった作業。

それを2年間やっていたせいか、脆弱性情報が公開されるとすぐに対応する癖みたいなものがついた。7時前から作業して検証して7時11分に PR を作成した。レビューアは誰も作業を始めてないけど。金曜日は非稼働日なので私が作業しなくてもよいのだけど、ここまでやったら安心して他の作業に移ることができた。

生田川公園の桜

地元のコミュニティでオミクロン株の感染が落ち着いてきたのでリアルお花見をしたいねという話題があがっている。私自身、お花見に毎年参加するような人間でもないけれど、たしかにコロナ禍になってからはお花見やってないだろうし、個人的にも数年はお花見やってないからやってもいいかなという気持ちにはなった。近場だと 生田川公園 という場所があり、特筆するほど桜がとてもきれいという場所ではないが、一応は桜があって、お花見するスペースもあって、形としては成り立つようなところ。お仕事を終えてから自転車で開花状況を見に行った。19時頃に行って寒くても何組かはお花見している集団はいた。開花状況は7-8割といったところかな。今週末から来週にかけてぐらいが見頃だと思う。

log4j2 セキュリティ対応

log4j2 セキュリティ対応

23時に寝て5時に起きたが、だらだらしているうちに2度寝して6時半に起きた。

log4j2 セキュリティ対応

CVE-2021-44228 が金曜日のお昼から私のタイムラインを賑わしている。私がお手伝いしているお仕事はイントラのシステムなのでやや余裕をもって情報を眺めていた。issue のコメント をみても log4j 1.x にも影響があると書かれて、その後に実際には影響ないと書かれて、さらにその後に条件付きだけど影響はあると二転三転してた。自分で実際に試してなくて世の中の開発者の情報をみているだけ。そのため、公式の情報を信頼するといったポジションでしかない。関係者の方々には敬意を払いたい。私は spring の公式ブログで公開されている Log4J2 Vulnerability and Spring Boot を読みながら対応した。

ターコイズ

ふとしたきっかけで ターコイズ の記事を読んだ。12月の誕生石らしく、それでいまの時期に紹介されることも多いのだと推測する。別の記事でターコイズは喉によいと書かれていて、以前 喉に違和感がある ことを書いた。日常生活に困るほどではないけど、もうこの歳だから体調が良くなることはなく悪くなる一方だろうという見通しも含めて験担ぎのような感覚で喉というキーワードでつながったから購入してみた。

近所の原石屋さんに行って尋ねてみたら1-2cmぐらいのサイズ1個240円ほどで売っていたので3個買って、近所のダイソーで入れものを買って、それっぽくオフィスに置いておくことにした。うちのコーポレートカラーはグリーンとブルーなんだけど、ターコイズも ターコイズグリーンターコイズブルー の2種類の色がある。創業も12月なので誕生石としても合致する。共通点があって相性がよさそうなのでうちのコーポレートストーン (そんな言葉ない) はターコイズでいいや。