ばぁど・うぉっちんぐ

セキュリティに強いWeb屋。自由と春を求めて羽ばたく渡り鳥。

このブログはGoogle Analyticsを利用しています

闇の魔術に対抗するための正攻法

どーも。ばぁどです。

ハリーポッターは好きよりの好きです。 2023年のビッグニュースとして、ハリーポッターが年末(12月31日)より、配信がされるとのことです!!! 2023年の年末と、2024年の年始はハリーポッター見ながら実家でまったりと過ごそうと思います。

Amazon Prime Video 12月は「スーパーマリオ」や「ハリポタ」など魔法ワールド11作 - AV Watch

さて、IT業界にはさまざま闇の魔術があります。 その闇の魔術一つが、プロジェクトに埋め込まれる致命的なバグや緊急性の高い脆弱性が埋め込まれやすくする方法というものがあります。 今回は、これらのバグや脆弱性が埋め込まれないための正攻法をご紹介します。

余計な開発をするな。既にあるものを使いなさい。

要は実業務において「車輪の再開発」は行わないようにしましょう、ということです。 人間はミスをする生き物です。どんなに完璧だと思っていても、開発規模が大きくなるとそこに含まれるバグは多くなるのが定石です。 既に作成されているライブラリがインターネット上にあるのであれば、そのライブラリを使いましょう。

世界中に優秀なエンジニアがいます。顔も知らない誰かですし、言語が通じるかもわかりません。それでも、世界中にはたくさんの優秀なエンジニアがおり、常に新しい便利なライブラリを開発し続けてくれています。

筆者が新人の時にカレンダーのUIで日付を選択したい場合に自前で実装しようとした時に、近くにいた先輩に便利なライブラリがあることを教えてもらって感動をした覚えがあります。

jqueryui.com

もちろんライブラリを使用する際は、バグがないかや、本当にセキュリティ的に安全なのか、脆弱性が埋め込まれていないかは確認する必要はありますが、一般的に利用頻度が多いことが確認されているライブラリであれば、基本的には問題ないと考えて良いと思います。

仮に、既に開発がされているライブラリがあるにもかかわらず、自前でそれらの機能を実装しようとすると、そこにはバグや脆弱性が含まれる温床となります。 もちろん、安全な開発をできる環境があり、ソースコードレビューを適切に行い、それらの関数の脆弱性チェックなどができ、万全の体制を整えることができるチームなら杞憂で終わると思います。 しかし、大半のプロジェクトチームは運用チームからの新しい要望や、サービス拡大に伴うシステム改修で手一杯なはずです。それらのライブラリに対して、莫大なコストを支払う余裕ないのであれば、大人しく既存のライブラリを使いましょう。

身の丈のあった技術選定を

技術選定はプロジェクト開発において非常に重要です。 プログラム言語を何にするか?使用するフレームワークは何にするか?クラウド技術はAWSにするかGCPにするか? さまざまな場面で判断が迫られます。

技術選定を行う際は、さまざまな事情を考慮して選定されるのですが、稀に「技術的なチャレンジをするために最新技術を用いた開発」を行うという名目上、新しい技術が採用される場合があります。 しかし、この挑戦的な技術選定は稀に大量のバグと脆弱性を埋め込む可能性があります。

メンバーが不慣れな技術だと、開発する際に遅延が発生する可能性はあり、技術仕様を把握しきれていないことからくるセキュリティバグが埋め込まれる可能性が上がります。

しかし新しい挑戦をしないと技術的な成長が止まってしまうということも事実です。 新しい技術に挑戦する際は、事前にメンバーにはチュートリアルを回すことを徹底したり、挑戦したい技術の入門書を買ったり、一人でも良いので熟練者をプロジェクトチームに入れるなど、むやみに挑戦するのではなく、ある程度のリスクヘッジをした上で、挑戦するのが良いと思います。

奇を衒わず、正攻法で行きなさい

プロジェクト開発は常に基本を疎かにしないことをお勧めします。 奇を衒って、設計したプロジェクトはたいていがバグや脆弱性の温床になることが多くあります。

例えば、サーバから値を返却してクライアント側で描画する際は、フレームワークのルールに従って実装することで大抵の脆弱性は考慮せ図にWebアプリケーションを開発することができます。 特にXSSなどの画面に描画する際に発火するような脆弱性であれば、フレームワークのルールに従って実装することで無害化(エスケープ処理)された状態で、画面に出力されます。 しかしフレームワークのルールに従わずに実装した場合は、これらのバグや脆弱性が埋め込まれる可能性が高まります。

他にもGETメソッドでリソースの更新を行なったり、何でもかんでもPOSTメソッドで実装したりするなど、本来の利用目的とは違う場合や、開発者が意図した使用方法ではない場合などは、大体設計の仕方が変だったり、仕様を達成するために少々無茶な設計をしていることも多くあります。

このような設計があった場合や、ソースコードがあった場合はバグや脆弱性の温床となります。 常に技術は正しく使い、常に用法用量をお守りください。

まとめ

少しでも世の中のプロダクトがセキュアになりますように。

久方ぶりの開発合宿 2023.07.15-07.17

どーも。ばぁどです。

7月の海の日の三連休を使って開発合宿に行ってまいりました。 開発合宿への参加は、コロナ前が最後であったため約3年ぶりでしょうか。

今回は開発合宿に参加したので、そのアウトプットも含めて備忘録とします。

銚子の海
銚子の海

開発合宿とは?

2泊3日で、旅館に泊まり開発をするイベントです。 前職の企業のメンバーを主体に、開発合宿という文化があり、筆者も未だに参加させていただいているイベントになります。

イベントの内容としては、旅館に行きただひたすら開発を行うだけという非常にシンプルなものになります。

会場

毎回お世話になっている旅館は下記です。 土善旅館さん。(土には、があります。)

www.dozenryokan.com

毎回ご飯がとても美味しいです。 聞いたところ、こしひかりだったのですが、家でこしひかりを炊いても同じ味にならない・・・なぜ。

久方ぶりの開発合宿に参加して

.プログラミングは楽しいもの

現在の企業に転職して、そろそろ2年を超え、3年目に突入します。 筆者は現在、脆弱性診断を生業としており、プログラミングなどを用いた開発業務からは遠ざかっております。

開発合宿はコロナ禍は開催されないイベントであったため、開発合宿を目標にした開発なども行っていませんでした。

しかし今回の開発合宿で改めて感じたことが「ものづくりって楽しいですね。」ということ。

開発合宿は良いモチベーションになる

開発合宿はとても良いモチベーションになります。

なぜならば、開発作業というものに必然と向き合う時間が与えられるため、それに向けての最小限の準備をすることになります。 今回の開発合宿への参加がなければ、改めて開発に向き合うこともなかったので、個人的には良いきっかけになりました。

脆弱性診断のその先にあるもの、次のキャリアを考えているのですが、やはりもう少し開発に寄せたエンジニア人生を歩んで行きたいなと考えております。

開発の感覚を取り戻すの難しい

やはりブランクというものはありますね。 脆弱性診断を2年ほど行っていますが、業務でのプログラミングをする機会がめっきり減ってしまい、プログラミングの勘を取り戻すのに苦労しました。

やはりアルゴリズムを考える脳が、普段業務で使っている部位とは違う部分の脳みそを動かさなければいけないため、そういった疲れもあったのかなと思います。

業務でプログラミングを触らないとは言いましたが、ちょくちょく空き時間で業務改善ということで、Excelのマクロを組んだりはしているのですが、一晩考え直したら20行のコードが5行になったこともあり、一発で良いアルゴリズムを思いつく勘が鈍っているなと感じた直後の開発合宿だったので、そういった勘を取り戻すのにも、とても重要なイベントでした。

まとめ

開発合宿次回も行きまーす!

写真は今年のODD(Osake Driven Development)で使用したお酒。

ChatGPTにプログラムを書かせてみて、色々と検証してみました。プログラマはAIにより駆逐されてしまうのか?

どーも。ばぁどです。

ChatGPTが話題になり数ヶ月ですが、やっとアカウント登録して使ってみました。 プログラマの仕事が奪われるとか、色々SNSで見たりしましたが、 百聞は一見にしかず!と言うことで!

ポーカープログラムについて

筆者もPythonの練習がてら、ポーカープログラムを2,3年前に書いていました。 デッキからカードを引いたり、役を判定したりはできるのですが、まだ対戦機能は追加しておりません。(2023/03/26時点)

github.com

今回は、業務ロジックや業務知識などは必要ない、このポーカーのロジックをPythonで書いてもらいました。

ChatGPTによるポーカープログラム

最初のご挨拶

次に、ChatGPTが出して来てくれたポーカープログラム

出力されたPython

import random

# デッキの初期化
suits = ["ハート", "ダイヤ", "スペード", "クラブ"]
ranks = ["エース", "2", "3", "4", "5", "6", "7", "8", "9", "10", "ジャック", "クイーン", "キング"]
deck = [(rank, suit) for suit in suits for rank in ranks]
random.shuffle(deck)

# ゲームに参加するプレイヤーの数を入力
num_players = int(input("プレイヤーの数を入力してください: "))

# プレイヤーの手札を初期化
player_hands = [[] for _ in range(num_players)]

# カードを配る
for i in range(5):
    for j in range(num_players):
        card = deck.pop()
        player_hands[j].append(card)

# プレイヤーの手札を表示
for i, hand in enumerate(player_hands):
    print(f"プレイヤー{i+1}の手札: {hand}")

ChatGPTも言っていますが、デッキやカードを引くなどをしているだけで、役の評価や対戦ロジックはありません。 しかし上記コードだけだとトランプのデッキを作って、手札を配っているだけになります。 (それだけでも十分すごいのですが・・・) 変数の付け方がとても綺麗。 無駄なfor文もありません

# プレイヤーの手札を初期化
player_hands = [[] for _ in range(num_players)]

個人的に上のような書き方ではなく冗長に書かれた方が好きなのですが、今回は複数人での対戦を想定しているため、これは一つの形として良いですね。

次に評価ロジックも書いてもらいました。

出力されたPython

# 5カードドローの手札の役を判定する関数
def evaluate_hand(hand):
    # 手札をカードのランクとスートに分ける
    ranks = [card[0] for card in hand]
    suits = [card[1] for card in hand]
    
    # ランクの出現回数をカウントする
    rank_count = {rank: ranks.count(rank) for rank in ranks}
    
    # 手札にエースが含まれるかどうかを判定する
    has_ace = "A" in ranks
    
    # ストレートを判定するために、ランクを数値に変換する
    rank_values = {
        "2": 2, "3": 3, "4": 4, "5": 5, "6": 6, "7": 7, "8": 8, "9": 9,
        "T": 10, "J": 11, "Q": 12, "K": 13, "A": 14
    }
    
    # ストレートの判定
    sorted_ranks = sorted(set(ranks), key=lambda x: rank_values[x])
    is_straight = False
    if len(sorted_ranks) == 5 and (int(rank_values[sorted_ranks[-1]]) - int(rank_values[sorted_ranks[0]]) == 4):
        is_straight = True
    elif sorted_ranks == ["2", "3", "4", "5", "A"]:
        is_straight = True
    
    # フラッシュの判定
    is_flush = len(set(suits)) == 1
    
    # ロイヤルフラッシュの判定
    is_royal_flush = False
    if is_flush and has_ace and set(ranks) == {"T", "J", "Q", "K", "A"}:
        is_royal_flush = True
    
    # ストレートフラッシュの判定
    is_straight_flush = False
    if is_straight and is_flush:
        is_straight_flush = True
    
    # フォーカードの判定
    is_four_of_a_kind = False
    if 4 in rank_count.values():
        is_four_of_a_kind = True
    
    # フルハウスの判定
    is_full_house = False
    if set(rank_count.values()) == {2, 3}:
        is_full_house = True
    
    # スリーカードの判定
    is_three_of_a_kind = False
    if 3 in rank_count.values():
        is_three_of_a_kind = True
    
    # ツーペアの判定
    is_two_pair = False
    if list(rank_count.values()).count(2) == 2

こう言ったロジックを、確実に人間が書くよりも素早く的確に出してくれるのは驚嘆します。 ポーカーのロジック判定って、初学者にとっては良い勉強ツールだと思っています。 配列の扱い方や、ツーペアなどの現実で人間が判定しているロジックを、プログラムに落とし込むと言う練習は非常に重要です。 ただ、そう言ったロジックを学ぶのではなく、単純に作るだけなのであればAIが圧倒的に有利と言ったところ。

ただ、単純にPythonでコードを書くと、あまり保守性がないように見受けられます。 特にDeckやCardなど、クラス化できるような部分が、個人的には不満です。

そこで、ChatGPTにこう言った指示を出してみました。

出力されたPython

import random

# カードのランクとスートを表す定数
RANKS = ["2", "3", "4", "5", "6", "7", "8", "9", "T", "J", "Q", "K", "A"]
SUITS = ["C", "D", "H", "S"]

class Card:
    def __init__(self, rank, suit):
        self.rank = rank
        self.suit = suit
    
    def __repr__(self):
        return f"{self.rank}{self.suit}"
    
class Deck:
    def __init__(self):
        self.cards = [Card(rank, suit) for rank in RANKS for suit in SUITS]
        self.shuffle()
    
    def shuffle(self):
        random.shuffle(self.cards)
    
    def draw(self):
        return self.cards.pop()
    
class Hand:
    def __init__(self, cards):
        self.cards = cards
    
    def add_card(self, card):
        self.cards.append(card)
    
    def discard(self, card_index):
        return self.cards.pop(card_index)
    
    def __repr__(self):
        return ", ".join(str(card) for card in self.cards)

しっかりと指示を出せば、カードやデッキなどをクラス化したPythonを出力してくれましたね! すごい!

そして、既存のコードを読み込んでもらって改善してもらうこともできました。

1.Playerクラスにプレイヤーの名前を保存するname属性を追加します。

class Player:
    def __init__(self, name):
        self.name = name
        self.hand = []

2.対戦するプレイヤーの名前を取得する関数を追加します。

def get_player_names():
    print("Enter player names (comma separated): ")
    names = input().strip().split(",")
    return names

3. プレイヤーの名前を取得して、Playerオブジェクトを作成する関数を追加します。

def create_players():
    names = get_player_names()
    players = []
    for name in names:
        player = Player(name.strip())
        players.append(player)
    return players

4. ゲームの進行を制御するmain関数内に、create_players関数を呼び出してプレイヤーを作成し、対戦させる処理を追加します。

def main():
    deck = Deck()
    players = create_players()
    for player in players:
        print("Player: {}".format(player.name))
        hand = deck.draw(5)
        player.hand = hand
        print("Hand: {}".format(hand))
    winner = determine_winner(players)
    print("Winner: {}".format(winner.name))

if __name__ == "__main__":
    main()

実際に上記コードを追加して、ソースコードが正しいかのチェックはまだしておりません。 今まで億劫だったので、やっていませんでした。 なので、ChatGPTに投げてみました!

import random

def deal(deck, num_cards):
    hand = []
    for i in range(num_cards):
        card = deck.pop(random.randint(0, len(deck) - 1))
        hand.append(card)
    return hand

deck = Deck()
deck.shuffle()
player1_hand = deal(deck.cards, 5)
player2_hand = deal(deck.cards, 5)
# 対戦
player1_score = judge(player1_hand)
player2_score = judge(player2_hand)

print("Player1 hand:", player1_hand, "Score:", player1_score)
print("Player2 hand:", player2_hand, "Score:", player2_score)

if player1_score > player2_score:
    print("Player1 wins!")
elif player1_score < player2_score:
    print("Player2 wins!")
else:
    print("It's a tie!")

内部のロジックなどは、書いてくれてはいませんがある程度機能の中身も理解できる。 こう言った、人間が必死に考えずともロジックを投げてくれるなーという感覚ではあります。

プログラマはAIにより駆逐されるのか?AIが普及してもプログラマに必要な技術とは?

個人的な答えは、平坦なプログラマは駆逐されます。 それこそ、指示待ちのプログラマやプログラムを書くだけのプログラマです。 しかし優秀なプログラマはChatGPTなどのAIを用いて、更に高度なエンジニアリングをできるようになるかなと思います。

プログラムの良し/悪しを判断する技術

AIが出してくれるプログラムが良いものかどうかを判断するのは人間です。 用件定義不足や、AIが間違える場合もあります。 それらのAIが出してきたコードが正しい動きをするのか?と言うのは非常に重要な部分だと思います。

今回はポーカーアプリを作ってもらいましたが、じゃあ今後プログラムにおいてプログラマがポーカーのロジックを考えなくて良いか?というと、そう言うわけではないと考えています。 やはりプログラムロジックを考える力がないと、 実業務をプログラムとして書き起こすことは難しいですし、複雑なビジネスロジックをどこまでAIに任せるかはまだ十分な議論がされていません。

ベンチャーであれば、あるほどAIの業務の取り組みは早いかもしれませんが、ガチガチなルールで縛られた企業ではAIの活用にはまだ数年かかるかもしれませんね。 どちらにせよ、AIはツールとして活用するべき強力なツールだと学びました。

IT領域にも”藤井聡太"のような異次元のエンジニアが現れる

チェス業界や将棋業界などの、ある特定のテーマにおけるAI研究は盛んに行われていました。 筆者が高校生の時には既に研究が始められており、チェスの王者がAIに負けたと言うコラムを読んだ覚えがあります。

そんな現在将棋界を席巻している藤井聡太さんは、子供の頃からAIを用いて将棋の勉学に励んでいたそうです。 もちろん現役の棋士の皆様もAIを用いた将棋研究は行なっていますが、幼少期の頃からAIによる将棋の研究をしていることから、積んでいるエンジンがそもそも違うといった各棋士のコメントをよく読みます。

ChatGPTなどのAIが今後更に普及することにより、プログラムの学習時点で効率よくAIを用いる超絶エンジニアが出てくる可能性があります。 そう言ったすごい若手エンジニアとも戦わなければいけないとなると、余計窮屈になってしまうなと考えるだけで頭が痛いですね。

最後にAIに聞いてみた

今のところは大丈夫っぽいですね(苦笑

”適応障害”と診断されたエンジニアの復職までの奮闘記

どーも。ばぁどです。 個人的な備忘録です。

今年のとある時期に、”適応障害”と診断されて一時期休職しておりました。 今回は自身の適応障害になった事象と、復帰までの備忘録になります。

※筆者は精神科に関するプロフェッショナルではありません。 本記事に記載されている医療的な内容に関して責任は負いかねます。適切に主治医と相談をしてください。

適応障害とは

自分の置かれた環境にうまく慣れることが出来ず、不安感や抑うつ気分、不登校、出勤拒否、対人トラブルなど、様々な症状・問題が出現し、社会生活に支障をきたす状態です。
適応障害は様々な要因で起こりえますが、特に就学や就職、転職、結婚、離婚など、生活環境が大きく変わった際に発症しやすいと言われています。ご本人が「新たな環境にうまく適応しなくては」と思ってもなかなか思い通りに事が運ばない、そのようなストレスが原因となります。
不安感を引き起こしている原因ははっきりしている事が多く、原因から離れることで症状の改善が見込めます。しかし現実には、転職や転校などの方法で環境を変えることが難しい状況もあります。ストレスの原因から離れることが出来ずに症状が長期間続くこともあります。

https://sobani-clinic.com/maladjustment.htmlより引用

Google検索で一番上に出てきたメンタルクリニックの説明を引用させていただいております。 他のサイトでも同じようなことが書かれており、実際に私も主治医より上記のような説明を受けていたので、内容としては問題ないはず。

筆者としましては、最初に「適応障害」と診断された時は「あ、なんか聞いたことある!」くらいの感じでした。

具体的な症状とストレスの原因

具体的な症状です。 具体的な症状は、業務中に出ました。 仕事中に急に不安になる、動悸が止まらない、注意力散漫になるなど、普段とは違うことが多々ありました。

あまりにも普段とは違うことがあり、特に普段はミスをするはずがないところでのミスが目立ちました。 ミスをした上で自分でさらに自分を追い込み、さらにメンタルに不調をきたすという悪循環に陥りました。

少しプライベートでも影響は出ており、普段はあり得ないミスを日常生活でもしていたので、やはり変だったのでしょう。

ただ、深刻な症状は業務中にのみ現れていたため、プライベートでは元気になります。 仕事終わって数十分すれば、気分は晴れやか。 今日はご飯何を食べに行こうとか、この後何の映画をアマプラで見よう!とか、色々と”楽しい”ことは考えることができました。

ストレスの原因としては、業務に出ていたので間違いなく仕事内容です。 1年弱同じ仕事をしていたのに、突然なったということなので、 おそらく直近の案件で変なストレスの掛け方をしてしまったのかなと分析しております。

元から、あまり残業を好まない考え方をしていたので、 少し残業?と言いつつも、あまり残業もしていなかったのでさてはてなんでしょう?といった感じです。

どのように治療を行ったか

ひたすら仕事を忘れました。 学生時代の友人に連絡を取り、旅行やご飯、ドライブに行く計画をひたすら立てました。 一人になると、どうしても仕事のことを考えたり、仕事に戻れるのか心配になったりしてしまうのですよね。 そういう状況に陥らないためにも、ひたすら人に会う予定を入れておりました。

旅行もなるべくするようにして、宮城旅行、静岡弾丸旅行、島根旅行など時間”だけ”はあるので、旅行しまくりました。 旅行やご飯に付き合ってくれた学生時代の友人に感謝でございます。

復職一ヶ月前(休職してから3週間後くらい)から、少しずつ勉強を再開。 勉強ではなくても良いのですけれども、何か机に向かって作業をするようなことに慣れることが目的でした。 仕事に関する勉強は少し辛そうなので、ずっと取得したいと思っていたダイビング資格の勉強をしました。 ダイビングは物理や自然保護などを学んだ後、海での実技の講習もあるので海においてリフレッシュすることができ、非常に良いリハビリだったと思います。

その後はここ数年チャレンジ目標においていたCEHを受験。無事に合格することができました。

復職!

まぁ、リフレッシュに全振りしていたので二ヶ月ほどで職場復帰。 最初の方は職場に慣れる意味で、時間制限(勤務時間は午前中のみや短期)があるかなと思ったら、二ヶ月での復帰は早いらしく最初からフルタイムでした。 まぁ個人的にも初日から問題なくフルタイムで働くことができたので、問題ないです。

適応障害になってみて。

マジでメンタルおかしくなると”気合い”とかでどうにかなるものではないですね。 思った以上に、自身の心の舵取りができなくなる? 舵が壊れてしまうので、大海原をただただ漂流するような不安感、焦燥感に駆られます。

適度にリフレッシュしていくことが大事。 頑張りすぎず、マイペースに。

あともっとプライベートや趣味に時間を割こうと考えております。 社会人になって、システムエンジニアを仕事として結構勉強ばかりしてきた。 でも、その勉強も一呼吸ついてスロースペースにしても良いのかなと。

引越しやプライベートでやりたいことなど、色々とやりたいことが増えてきたので復調したのでしょう。

そんないろいろな学びも得ることができた休職二ヶ月でした。

まとめ

健康第一!

※写真は休職期間中に訪れた島根県隠岐諸島海士町の港と海

Amazon Cognitoが脆弱性を入れ込まないと言う面でも素晴らしいと言う話

どーも、ばぁどです。 セキュリティエンジニアやっています。 元々はWebアプリ開発をやっていました。 現在は脆弱性診断を主にやっております。

最近、プライベートでAmazon Cognitoを利用したアプリケーションを触るタイミングがありました。 前から、Amazon Cognitoの存在はなんとなく知っておりましたが、少し調べてみるとサイバーセキュリティ的な観点で「あぁ脆弱性がなくなる良いものだ」と言う感想を持ちました。

物は作り込まない方が脆弱性は入り込まないと言う鉄則

筆者がWebアプリ開発者として、Webアプリを開発していた頃のお話です。 「自身が作るよりもライブラリなどに任せた方が結果的に安全なWebアプリケーションが作れる」と言う旨の発言をする同僚がいました。 当時の筆者は、あまり理解できていなかったのですが今なら概ね同じ意見であります。

例えばWebアプリケーションのモデル層で、DBを操作するSQLを発行する場面。 今ならDBを操作するSQLを発行するためのライブラリは多くの言語、フレームワークで採用されており、それらのライブラリを正しく扱えば、SQLインジェクションなどの脆弱性は基本的に防ぐことが可能です。

クロスサイトスクリプティングなども同様に、フロントエンド側の技術を正しく扱えばエスケープ処理を施した上で画面への描画が可能です。

これらは誤解を恐れずにいうと、利用ライブラリがOSSとなっており幾人もの凄腕エンジニアの方々のチェックが入ることから脆弱性が存在しないことが担保されています。

この既に作られているライブラリの安全性を理解していないと、自前のライブラリを使うとか、社内独自のフレームワークという発想になり、そもそもそこに脆弱性が存在していて、脆弱性だらけのWebアプリケーションを量産するという構図になっている企業を稀に見ます。

基本的には「作り込まない方が脆弱性は入り込みません」。

Amazon Cognitoが脆弱性を入れ込まないと言う面でも素晴らしい

さて、Amazon Cognitoのお話になります。 Amazon Cognito とは awsが提供するサービスの一つになります。

Amazon Cognito は、ウェブおよびモバイルアプリの認証、承認、およびユーザー管理機能を提供します。ユーザーは、ユーザー名とパスワードを使用して直接サインインするか、Facebook、Amazon、Google、Apple などのサードパーティーを通じてサインインできます。
Amazon Cognito の主な 2 つのコンポーネントは、ユーザープールと ID プールです。ユーザープールは、アプリユーザーのサインアップとサインインオプションを提供するユーザーディレクトリです。ID プールは、AWS の他のサービスに対するアクセスをユーザーに許可します。ID プールとユーザープールは別々に使用することも、一緒に使用することもできます。

docs.aws.amazon.com

要するに、Amazon Cognitoを用いることでログイン処理(認証、承認)を比較的工数をかけずに作成することができます。 ログイン処理ということなので、もちろんユーザ管理機能や各種アカウントとの連携なども可能です。

ログイン処理(認証、承認)は一定の力量を持つエンジニアが設計、開発しなければならない

ログイン処理とは、会員制のWebアプリケーションを使用する際に、そのWebアプリケーションに”誰が”、”どういった権限”で利用するかのチェック機構になります。 ユーザID、パスワードを入力した際に、ユーザID はテーブル内に存在するか?パスワードは合っているか?などのチェック機構が基本的に入ります。 ユーザID及び、パスワードが合っていて初めてログインを行うことができます。

しかしログイン処理は、Webアプリケーションを利用していないユーザでもアクセスすることができる重要なシステムです。 例えば、存在しないIDを入力した際に出すエラーメッセージと、既に存在するIDを入力した際に出すエラーメッセージを工夫しないと、攻撃者に対してユーザ情報について教えてしまう可能性があります。

このように、ログイン処理は一定の力量を持つエンジニアが開発しなければ、攻撃者にとって絶好の攻撃ターゲットになってしまうことは想像に難くありません。

また、ID連携機能は更に高い技術力が求められます。 Open ID Connect などの企画はありますが、それらの仕様を把握した上でテーブル設計を行い、漏れなくロジックを書くことによって初めて実現されるのが他システムとのID連携になります。 正直筆者も実装を行うとなうと、身震いしてしまうくらいには避けたいシステム内容です。

Amazon Cognitoが素晴らしい。

そこでAmazonから提供されている、Amazon Cognitoです。 Amazon Cognitoを用いれば上記の本来はログイン機能を実装する際に考慮しなければいけない内容を考慮せずに、Amazonデファクトスタンダードに合わせてログイン機能を用いることができます。

ログイン処理を開発する際に考慮するべき、ユーザのテーブル設計などもAmazonが用意してくれています。 この考えなくて良いというのと、あらかじめセキュリティが担保されているというのは、Webアプリ開発の知見を持たないベンチャー企業にはとても有益なのではないでしょうか。

正直エンジニアとしての経験をまともに3〜5年くらい続けていればログイン機能の一つや二つは開発する機会はあるでしょう。 しかしセキュアなログイン機能を完璧に開発できるかは、その当時の仕様やソースコードのチェック体制にも絡んでくる要素であり、筆者自身もセキュアなログイン機能を実装するのは可能ですが、大きな工数が必要になります。 こういった工数削減という面から見てもAmazon Cognitoは非常に有益です。

また、ログイン時のパスワードのポリシーなども既に用意されているものを扱えば、基本的には安全なものになります。 例えばパスワードの最低文字数、最長文字数や文字種別などです。

docs.aws.amazon.com

脆弱性診断のタイミイングでこれらの要件に不備があることを指摘されても、管理コンソールから設定を修正することでセキュアなログインポリシーの反映ができます。 これを自前で開発していると、if分を追加したりだとか、エラーメッセージをどのように表示するかなどを考える必要があります。

こういった点から、Amazon Cognitoなどを利用した方がセキュアなログイン機能を得ることができ、とても有益だと筆者は考えました。

新しい技術は正しく採用することが吉である。

筆者個人的な感想ですが、新しい技術は正しく採用していくことは吉だと考えています。 特にAmazon Cognitoのように、採用するだけで一定のセキュリティを担保できるような技術は採用の価値は十分にあるでしょう。 個人的にはAmazon Cognitoの管理画面上で、セキュリティポリシーなどをチェックボックスで入力することで変更できる部分はとても感動しました。(まぁそりゃそうなのだが)

しかし技術選定はケース by ケースであり、 こういった最新の技術を使用するのが会社のルール的に難しい場合もあれば、 どうしてもAmazon Cognitoの仕様がWeアプリケーションの仕様とマッチしない場合もあるでしょう。

そういった場合は、自身の置かれている環境と、新しい技術のメリット/デメリットを考慮した上で、採用を検討してもらえればと思います。

リベンジ成功!!CEH合格体験記!!

どーも。ばぁどです。 久々のブログ更新になりました。 ちと最近色々ありまして、勉強とかしないようにしていたのでアウトプットも少なめ。

そんな中、CEHに合格したので合格体験記を書いていきます。

CEHとは

CEHとはCertified Ethical Hacker という略で、倫理的な認定ハッカーという意味を持つ資格です。 アメリカの企業であるEC-Councilが主催しており、海外では一定の評価を得られているセキュリティ系の資格になります。

www.eccouncil.org

初挑戦は2020年12月

はい。筆者、一度CEH落ちています。 当時は、独学で頑張ろうとなり、EC-Councilにセキュリティに関して2年の実績ありますよと、拙い英語で説明を行い、海外から電話がかかってくるなどの難所を突破し、無事に受験資格を得た上で試験に挑みました。

当時はCEHのトレーニングを受ける以外では日本語での受験をすることができず、言語を英語で挑戦しました。 その結果、敗北。

毎朝英会話をやっているので、 少し英語に自信はあったのですが、やはり試験を受けるほどまで英語力が醸成されていなかった模様。

また、敗着の原因としてはnmapのコマンドなどを勉強しておらず、3問ほど全て落としてしまったのも原因に挙げられるかと思います。

念願のリベンジ!2022年10月

そんな、CEHに敗北してから2年後、CEHへのリベンジを果たしました。

転職をした先の会社でCEHのトレーニングを受ける人を募集しており、飛びつきました。 2021年中にトレーニング自体は終了。 仕事の繁忙期や、メンタル・体調の調整、勉強時間をなんとか捻出し、トレーニングを受けた後10ヶ月ほどで試験に挑みました。

勉強期間は、メンタルの浮き沈みがあったのですがトータルで2ヶ月半くらいかなと思います。 CEHのトレーニングで配布されたテキストに付箋を貼りながら、必死にノートにまとめ、後述するPocketPrepで苦手分野を埋めていきました。

その結果、72%というギリギリのスコアで、無事にCEHに合格ました。

個人的なCEHを受ける上で気をつけるべきところ

範囲が非常に広い

試験範囲が非常に広いです。 また、IPAの試験とは違いベンダーの製品なども出てきます。

このことからある程度日本語でセキュリティを一通り勉強してから挑戦した方が良いかなと思いました。

筆者は4年前くらいに情報処理安全確保支援士に合格したり、一時期サイバーセキュリティの講師なども行っていたため、その際の知識が非常に役立ったと思います。

特に情報処理安全確保支援士は、CEHの試験範囲と重なる部分もあり、情報処理安全確保支援士の試験範囲ではない部分を苦手分野として、集中的に勉強を行いました。

このように試験範囲は非常に広いので気をつけてください。

nmapのコマンドは確実に覚える

Nmapのコマンドは確実に覚えた上で、試験に臨んでください。 試験問題は毎回ランダムのはずですが、3問-4問ほど出てきました。 普段業務で使用していればおそらく問題ないのですが、筆者はnmapを業務では使用していない側の人間。

Nmapの基本的なコマンドは下記サイトを参照。

nmap.org

Nmapのコマンドは、SYNやFINスキャン、Xmasスキャンなどそれぞれがどういったスキャンなのかをセットで覚えると吉です。

中途半端な日本語翻訳に注意

CEHは基本的に英語です。 英語のものを日本語に訳して、意味を理解するといった作業が非常にありました。

例えば、OSI参照モデルだけでも日本語と英語で表現が違ったりします。 英語で初めての概念を勉強していたら、日本におけるOSI参照モデルやん!とかありました。

知らないツールは事前にまとめる、覚えていないものは諦める

後述する、模擬試験サイトである程度自信を持った上で挑みましたが、それでも初めて聞くツールが存在しました。

もしかしたらテキストをひたすら探れば、記載があったのかも知れませんが、ツール群に関しては当日の感でした。 対策の試験勉強としてはMACスプーフィングやDosなどの目的別のカテゴリを作成して、ひたすらツールをまとめていくという対策はできたかなと少し反省しました。

参考にしたサイト、本、勉強会など

Pocket Prep

個人的に一番活用させていただいたサービスです。 1,300問の模擬問題があり、使いやすさも抜群。 言語は英語のみなのですが、Google翻訳でひたすら翻訳すれば問題ないです。

www.pocketprep.com

Certified Ethical Hacker(CEH) Online practice exam

こちらも便利。 Pocket Prepでは出ない問題がいくつかあったので、知識の補填に役立てました。 しかしV10までしかなく、2022年10月現在v11での試験になりますので、バージョンが違うというのは注意してください。

ceh.cagy.org

ホワイトハッカー入門

CEH対策に役だった本の一冊です。 内容は少し自信の知っている知識と食い違う部分もありましたが、あまり日本語で資料がまとまっていない上で、日本語で出してもらえている本なので非常に重宝しました。 特にnmapのコマンドのまとめ方は、この本が一番上手だったと思います。

book.impress.co.jp

勉強会(Conpass)

Conpassで有志により運営されている勉強グループです。 CEHホルダーが何名も参加してくれているので、勉強の仕方や、勉強してわからないことなどの質問もできると思います。 筆者も2回〜3回参加させていただき、有益な情報を得ることができました。 大変ありがとうございますmm 次回勉強会決まりましたら、ご挨拶程度で伺おうかなと思います。

ceh-studygroup.connpass.com

まとめ

CEH合格したぞーーーー!! 20代の頃に、30歳までにハッカーになる!と目標を掲げ、ギリギリ30歳でCEHの取得ができました。

別にCEHを取ったからといってハッカーになれたわけではないと思いますが、それでも資格として残るのは嬉しい限りでございます。

ひたすら続く社会人、ITという長い道。 その一つの通過点として、CEHというものがあったのかなと思います。 引き続き、日々精進です。

2022年11月16日追記

この記事を勢いで出した後、気づいたことがある。 それがASPENの画面にログインした時に気づいた。

ご覧の通り、一度私はCEHを落ちている。 当時は英語のリーディングが弱すぎて、落ちたものだと思っていた。 しかし、得点のパーセンテージを確認して把握した。

英語で受けたCEH v10

日本語で受けたCEH v11

上記を見てもらえれば分かる通り、実際は私が落ちた(Fail)したv10の方が1%多く得点している。 それにもかかわらず、今回受けた試験で72%で合格することができた。

結論:合格ラインが引き下げられたから合格できた。

ちゃんちゃん♪

 

BadStore に対して OWASP ZAP で動的検査を実施した結果

どーも。ばぁどです。 脆弱性診断を仕事としています。元Webアプリエンジニアです。 開発もできる脆弱性診断士を目指しています。

今回はやられ用のWebサイトであるBadStoreに、自動脆弱性診断ツールであるOWASP ZAPで動的に検査してみました。

OWASP ZAPの結果を貼り付けただけの雑記事です。

BadStore とは

やられ用のWebサイトです。 筆者はローカルプロキシツールであるBurpSuiteの拡張として入れました。

github.com

OWASP ZAP

脆弱性診断ツール。

www.zaproxy.org

感想

OWASP ZAPのレポートが非常に長いので、先に感想を。

自動脆弱性診断ツールは非常に便利。手動診断と比べても早く、網羅的に、人手を使わずにある程度の脆弱性を見つけてくれています。ツールごとに得意・不得意があったり、逆に手動診断でないと見つけることができない部分はあるはずなので、そういった理解を深めていきたい。

ZAP Scanning Report

Summary of Alerts

Risk Level Number of Alerts
High 6
Medium 3
Low 6
Informational 0

Alert Detail

Cross Site Scripting (Reflected)

High (Medium)

Description

Cross-site Scripting (XSS) is an attack technique that involves echoing attacker-supplied code into a user's browser instance. A browser instance can be a standard web browser client, or a browser object embedded in a software product such as the browser within WinAmp, an RSS reader, or an email client. The code itself is usually written in HTML/JavaScript, but may also extend to VBScript, ActiveX, Java, Flash, or any other browser-supported technology.

When an attacker gets a user's browser to execute his/her code, the code will run within the security context (or zone) of the hosting web site. With this level of privilege, the code has the ability to read, modify and transmit any sensitive data accessible by the browser. A Cross-site Scripted user could have his/her account hijacked (cookie theft), their browser redirected to another location, or possibly shown fraudulent content delivered by the web site they are visiting. Cross-site Scripting attacks essentially compromise the trust relationship between a user and the web site. Applications utilizing browser object instances which load content from the file system may execute code under the local machine zone allowing for system compromise.

There are three types of Cross-site Scripting attacks: non-persistent, persistent and DOM-based.

Non-persistent attacks and DOM-based attacks require a user to either visit a specially crafted link laced with malicious code, or visit a malicious web page containing a web form, which when posted to the vulnerable site, will mount the attack. Using a malicious form will oftentimes take place when the vulnerable resource only accepts HTTP POST requests. In such a case, the form can be submitted automatically, without the victim's knowledge (e.g. by using JavaScript). Upon clicking on the malicious link or submitting the malicious form, the XSS payload will get echoed back and will get interpreted by the user's browser and execute. Another technique to send almost arbitrary requests (GET and POST) is by using an embedded client, such as Adobe Flash.

Persistent attacks occur when the malicious code is submitted to a web site where it's stored for a period of time. Examples of an attacker's favorite targets often include message board posts, web mail messages, and web chat software. The unsuspecting user is not required to interact with any additional site/link (e.g. an attacker site or a malicious link sent via email), just simply view the web page containing the code.

Instances: 6

Solution

Phase: Architecture and Design

Use a vetted library or framework that does not allow this weakness to occur or provides constructs that make this weakness easier to avoid.

Examples of libraries and frameworks that make it easier to generate properly encoded output include Microsoft's Anti-XSS library, the OWASP ESAPI Encoding module, and Apache Wicket.

Phases: Implementation; Architecture and Design

Understand the context in which your data will be used and the encoding that will be expected. This is especially important when transmitting data between different components, or when generating outputs that can contain multiple encodings at the same time, such as web pages or multi-part mail messages. Study all expected communication protocols and data representations to determine the required encoding strategies.

For any data that will be output to another web page, especially any data that was received from external inputs, use the appropriate encoding on all non-alphanumeric characters.

Consult the XSS Prevention Cheat Sheet for more details on the types of encoding and escaping that are needed.

Phase: Architecture and Design

For any security checks that are performed on the client side, ensure that these checks are duplicated on the server side, in order to avoid CWE-602. Attackers can bypass the client-side checks by modifying values after the checks have been performed, or by changing the client to remove the client-side checks entirely. Then, these modified values would be submitted to the server.

If available, use structured mechanisms that automatically enforce the separation between data and code. These mechanisms may be able to provide the relevant quoting, encoding, and validation automatically, instead of relying on the developer to provide this capability at every point where output is generated.

Phase: Implementation

For every web page that is generated, use and specify a character encoding such as ISO-8859-1 or UTF-8. When an encoding is not specified, the web browser may choose a different encoding by guessing which encoding is actually being used by the web page. This can cause the web browser to treat certain sequences as special, opening up the client to subtle XSS attacks. See CWE-116 for more mitigations related to encoding/escaping.

To help mitigate XSS attacks against the user's session cookie, set the session cookie to be HttpOnly. In browsers that support the HttpOnly feature (such as more recent versions of Internet Explorer and Firefox), this attribute can prevent the user's session cookie from being accessible to malicious client-side scripts that use document.cookie. This is not a complete solution, since HttpOnly is not supported by all browsers. More importantly, XMLHTTPRequest and other powerful browser technologies provide read access to HTTP headers, including the Set-Cookie header in which the HttpOnly flag is set.

Assume all input is malicious. Use an "accept known good" input validation strategy, i.e., use a whitelist of acceptable inputs that strictly conform to specifications. Reject any input that does not strictly conform to specifications, or transform it into something that does. Do not rely exclusively on looking for malicious or malformed inputs (i.e., do not rely on a blacklist). However, blacklists can be useful for detecting potential attacks or determining which inputs are so malformed that they should be rejected outright.

When performing input validation, consider all potentially relevant properties, including length, type of input, the full range of acceptable values, missing or extra inputs, syntax, consistency across related fields, and conformance to business rules. As an example of business rule logic, "boat" may be syntactically valid because it only contains alphanumeric characters, but it is not valid if you are expecting colors such as "red" or "blue."

Ensure that you perform input validation at well-defined interfaces within the application. This will help protect the application even if a component is reused or moved elsewhere.

Reference

CWE Id : 79

WASC Id : 8

Source ID : 1

SQL Injection - SQLite

High (Medium)

Description

SQL injection may be possible.

Instances: 3

Solution

Do not trust client side input, even if there is client side validation in place.

In general, type check all data on the server side.

If the application uses JDBC, use PreparedStatement or CallableStatement, with parameters passed by '?'

If the application uses ASP, use ADO Command Objects with strong type checking and parameterized queries.

If database Stored Procedures can be used, use them.

Do *not* concatenate strings into queries in the stored procedure, or use 'exec', 'exec immediate', or equivalent functionality!

Do not create dynamic SQL queries using simple string concatenation.

Escape all data received from the client.

Apply a 'whitelist' of allowed characters, or a 'blacklist' of disallowed characters in user input.

Apply the principle of least privilege by using the least privileged database user possible.

In particular, avoid using the 'sa' or 'db-owner' database users. This does not eliminate SQL injection, but minimizes its impact.

Grant the minimum database access that is necessary for the application.

Other information

RDBMS [SQLite] likely, given error message regular expression [near ".+": syntax error] matched by the HTML results.

The vulnerability was detected by manipulating the parameter to cause a database error message to be returned and recognised

Reference

CWE Id : 89

WASC Id : 19

Source ID : 1

SQL Injection - Authentication Bypass

High (Medium)

Description

SQL injection may be possible on a login page, potentially allowing the application's authentication mechanism to be bypassed

Instances: 4

Solution

Do not trust client side input, even if there is client side validation in place.

In general, type check all data on the server side.

If the application uses JDBC, use PreparedStatement or CallableStatement, with parameters passed by '?'

If the application uses ASP, use ADO Command Objects with strong type checking and parameterized queries.

If database Stored Procedures can be used, use them.

Do *not* concatenate strings into queries in the stored procedure, or use 'exec', 'exec immediate', or equivalent functionality!

Do not create dynamic SQL queries using simple string concatenation.

Escape all data received from the client.

Apply a 'whitelist' of allowed characters, or a 'blacklist' of disallowed characters in user input.

Apply the principle of least privilege by using the least privileged database user possible.

In particular, avoid using the 'sa' or 'db-owner' database users. This does not eliminate SQL injection, but minimizes its impact.

Grant the minimum database access that is necessary for the application.

Reference

CWE Id : 89

WASC Id : 19

Source ID : 1

Path Traversal

High (Medium)

Description

The Path Traversal attack technique allows an attacker access to files, directories, and commands that potentially reside outside the web document root directory. An attacker may manipulate a URL in such a way that the web site will execute or reveal the contents of arbitrary files anywhere on the web server. Any device that exposes an HTTP-based interface is potentially vulnerable to Path Traversal.

Most web sites restrict user access to a specific portion of the file-system, typically called the "web document root" or "CGI root" directory. These directories contain the files intended for user access and the executable necessary to drive web application functionality. To access files or execute commands anywhere on the file-system, Path Traversal attacks will utilize the ability of special-characters sequences.

The most basic Path Traversal attack uses the "../" special-character sequence to alter the resource location requested in the URL. Although most popular web servers will prevent this technique from escaping the web document root, alternate encodings of the "../" sequence may help bypass the security filters. These method variations include valid and invalid Unicode-encoding ("..%u2216" or "..%c0%af") of the forward slash character, backslash characters ("..\") on Windows-based servers, URL encoded characters "%2e%2e%2f"), and double URL encoding ("..%255c") of the backslash character.

Even if the web server properly restricts Path Traversal attempts in the URL path, a web application itself may still be vulnerable due to improper handling of user-supplied input. This is a common problem of web applications that use template mechanisms or load static text from files. In variations of the attack, the original URL parameter value is substituted with the file name of one of the web application's dynamic scripts. Consequently, the results can reveal source code because the file is interpreted as text instead of an executable script. These techniques often employ additional special characters such as the dot (".") to reveal the listing of the current working directory, or "%00" NULL characters in order to bypass rudimentary file extension checks.

Instances: 1

Solution

Assume all input is malicious. Use an "accept known good" input validation strategy, i.e., use a whitelist of acceptable inputs that strictly conform to specifications. Reject any input that does not strictly conform to specifications, or transform it into something that does. Do not rely exclusively on looking for malicious or malformed inputs (i.e., do not rely on a blacklist). However, blacklists can be useful for detecting potential attacks or determining which inputs are so malformed that they should be rejected outright.

When performing input validation, consider all potentially relevant properties, including length, type of input, the full range of acceptable values, missing or extra inputs, syntax, consistency across related fields, and conformance to business rules. As an example of business rule logic, "boat" may be syntactically valid because it only contains alphanumeric characters, but it is not valid if you are expecting colors such as "red" or "blue."

For filenames, use stringent whitelists that limit the character set to be used. If feasible, only allow a single "." character in the filename to avoid weaknesses, and exclude directory separators such as "/". Use a whitelist of allowable file extensions.

Warning: if you attempt to cleanse your data, then do so that the end result is not in the form that can be dangerous. A sanitizing mechanism can remove characters such as '.' and ';' which may be required for some exploits. An attacker can try to fool the sanitizing mechanism into "cleaning" data into a dangerous form. Suppose the attacker injects a '.' inside a filename (e.g. "sensi.tiveFile") and the sanitizing mechanism removes the character resulting in the valid filename, "sensitiveFile". If the input data are now assumed to be safe, then the file may be compromised.

Inputs should be decoded and canonicalized to the application's current internal representation before being validated. Make sure that your application does not decode the same input twice. Such errors could be used to bypass whitelist schemes by introducing dangerous inputs after they have been checked.

Use a built-in path canonicalization function (such as realpath() in C) that produces the canonical version of the pathname, which effectively removes ".." sequences and symbolic links.

Run your code using the lowest privileges that are required to accomplish the necessary tasks. If possible, create isolated accounts with limited privileges that are only used for a single task. That way, a successful attack will not immediately give the attacker access to the rest of the software or its environment. For example, database applications rarely need to run as the database administrator, especially in day-to-day operations.

When the set of acceptable objects, such as filenames or URLs, is limited or known, create a mapping from a set of fixed input values (such as numeric IDs) to the actual filenames or URLs, and reject all other inputs.

Run your code in a "jail" or similar sandbox environment that enforces strict boundaries between the process and the operating system. This may effectively restrict which files can be accessed in a particular directory or which commands can be executed by your software.

OS-level examples include the Unix chroot jail, AppArmor, and SELinux. In general, managed code may provide some protection. For example, java.io.FilePermission in the Java SecurityManager allows you to specify restrictions on file operations.

This may not be a feasible solution, and it only limits the impact to the operating system; the rest of your application may still be subject to compromise.

Reference

CWE Id : 22

WASC Id : 33

Source ID : 1

Cross Site Scripting (Persistent)

High (Medium)

Description

Cross-site Scripting (XSS) is an attack technique that involves echoing attacker-supplied code into a user's browser instance. A browser instance can be a standard web browser client, or a browser object embedded in a software product such as the browser within WinAmp, an RSS reader, or an email client. The code itself is usually written in HTML/JavaScript, but may also extend to VBScript, ActiveX, Java, Flash, or any other browser-supported technology.

When an attacker gets a user's browser to execute his/her code, the code will run within the security context (or zone) of the hosting web site. With this level of privilege, the code has the ability to read, modify and transmit any sensitive data accessible by the browser. A Cross-site Scripted user could have his/her account hijacked (cookie theft), their browser redirected to another location, or possibly shown fraudulent content delivered by the web site they are visiting. Cross-site Scripting attacks essentially compromise the trust relationship between a user and the web site. Applications utilizing browser object instances which load content from the file system may execute code under the local machine zone allowing for system compromise.

There are three types of Cross-site Scripting attacks: non-persistent, persistent and DOM-based.

Non-persistent attacks and DOM-based attacks require a user to either visit a specially crafted link laced with malicious code, or visit a malicious web page containing a web form, which when posted to the vulnerable site, will mount the attack. Using a malicious form will oftentimes take place when the vulnerable resource only accepts HTTP POST requests. In such a case, the form can be submitted automatically, without the victim's knowledge (e.g. by using JavaScript). Upon clicking on the malicious link or submitting the malicious form, the XSS payload will get echoed back and will get interpreted by the user's browser and execute. Another technique to send almost arbitrary requests (GET and POST) is by using an embedded client, such as Adobe Flash.

Persistent attacks occur when the malicious code is submitted to a web site where it's stored for a period of time. Examples of an attacker's favorite targets often include message board posts, web mail messages, and web chat software. The unsuspecting user is not required to interact with any additional site/link (e.g. an attacker site or a malicious link sent via email), just simply view the web page containing the code.

Instances: 3

Solution

Phase: Architecture and Design

Use a vetted library or framework that does not allow this weakness to occur or provides constructs that make this weakness easier to avoid.

Examples of libraries and frameworks that make it easier to generate properly encoded output include Microsoft's Anti-XSS library, the OWASP ESAPI Encoding module, and Apache Wicket.

Phases: Implementation; Architecture and Design

Understand the context in which your data will be used and the encoding that will be expected. This is especially important when transmitting data between different components, or when generating outputs that can contain multiple encodings at the same time, such as web pages or multi-part mail messages. Study all expected communication protocols and data representations to determine the required encoding strategies.

For any data that will be output to another web page, especially any data that was received from external inputs, use the appropriate encoding on all non-alphanumeric characters.

Consult the XSS Prevention Cheat Sheet for more details on the types of encoding and escaping that are needed.

Phase: Architecture and Design

For any security checks that are performed on the client side, ensure that these checks are duplicated on the server side, in order to avoid CWE-602. Attackers can bypass the client-side checks by modifying values after the checks have been performed, or by changing the client to remove the client-side checks entirely. Then, these modified values would be submitted to the server.

If available, use structured mechanisms that automatically enforce the separation between data and code. These mechanisms may be able to provide the relevant quoting, encoding, and validation automatically, instead of relying on the developer to provide this capability at every point where output is generated.

Phase: Implementation

For every web page that is generated, use and specify a character encoding such as ISO-8859-1 or UTF-8. When an encoding is not specified, the web browser may choose a different encoding by guessing which encoding is actually being used by the web page. This can cause the web browser to treat certain sequences as special, opening up the client to subtle XSS attacks. See CWE-116 for more mitigations related to encoding/escaping.

To help mitigate XSS attacks against the user's session cookie, set the session cookie to be HttpOnly. In browsers that support the HttpOnly feature (such as more recent versions of Internet Explorer and Firefox), this attribute can prevent the user's session cookie from being accessible to malicious client-side scripts that use document.cookie. This is not a complete solution, since HttpOnly is not supported by all browsers. More importantly, XMLHTTPRequest and other powerful browser technologies provide read access to HTTP headers, including the Set-Cookie header in which the HttpOnly flag is set.

Assume all input is malicious. Use an "accept known good" input validation strategy, i.e., use a whitelist of acceptable inputs that strictly conform to specifications. Reject any input that does not strictly conform to specifications, or transform it into something that does. Do not rely exclusively on looking for malicious or malformed inputs (i.e., do not rely on a blacklist). However, blacklists can be useful for detecting potential attacks or determining which inputs are so malformed that they should be rejected outright.

When performing input validation, consider all potentially relevant properties, including length, type of input, the full range of acceptable values, missing or extra inputs, syntax, consistency across related fields, and conformance to business rules. As an example of business rule logic, "boat" may be syntactically valid because it only contains alphanumeric characters, but it is not valid if you are expecting colors such as "red" or "blue."

Ensure that you perform input validation at well-defined interfaces within the application. This will help protect the application even if a component is reused or moved elsewhere.

Other information

Source URL: http://127.0.0.1:8528/cgi-bin/badstore.cgi?action=doguestbook

Reference

CWE Id : 79

WASC Id : 8

Source ID : 1

SQL Injection

High (Medium)

Description

SQL injection may be possible.

Instances: 1

Solution

Do not trust client side input, even if there is client side validation in place.

In general, type check all data on the server side.

If the application uses JDBC, use PreparedStatement or CallableStatement, with parameters passed by '?'

If the application uses ASP, use ADO Command Objects with strong type checking and parameterized queries.

If database Stored Procedures can be used, use them.

Do *not* concatenate strings into queries in the stored procedure, or use 'exec', 'exec immediate', or equivalent functionality!

Do not create dynamic SQL queries using simple string concatenation.

Escape all data received from the client.

Apply a 'whitelist' of allowed characters, or a 'blacklist' of disallowed characters in user input.

Apply the principle of least privilege by using the least privileged database user possible.

In particular, avoid using the 'sa' or 'db-owner' database users. This does not eliminate SQL injection, but minimizes its impact.

Grant the minimum database access that is necessary for the application.

Other information

The page results were successfully manipulated using the boolean conditions [ZAP' AND '1'='1' -- ] and [ZAP' AND '1'='2' -- ]

The parameter value being modified was NOT stripped from the HTML output for the purposes of the comparison

Data was returned for the original parameter.

The vulnerability was detected by successfully restricting the data originally returned, by manipulating the parameter

Reference

CWE Id : 89

WASC Id : 19

Source ID : 1

X-Frame-Options Header Not Set

Medium (Medium)

Description

X-Frame-Options header is not included in the HTTP response to protect against 'ClickJacking' attacks.

Instances: 39

Solution

Most modern Web browsers support the X-Frame-Options HTTP header. Ensure it's set on all web pages returned by your site (if you expect the page to be framed only by pages on your server (e.g. it's part of a FRAMESET) then you'll want to use SAMEORIGIN, otherwise if you never expect the page to be framed, you should use DENY. ALLOW-FROM allows specific websites to frame the web page in supported web browsers).

Reference

CWE Id : 16

WASC Id : 15

Source ID : 3

Application Error Disclosure

Medium (Medium)

Description

This page contains an error/warning message that may disclose sensitive information like the location of the file that produced the unhandled exception. This information can be used to launch further attacks against the web application. The alert could be a false positive if the error message is found inside a documentation page.

Instances: 1

Solution

Review the source code of this page. Implement custom error pages. Consider implementing a mechanism to provide a unique error reference/identifier to the client (browser) while logging the details on the server side and not exposing them to the user.

Reference

CWE Id : 200

WASC Id : 13

Source ID : 3

X-Frame-Options Header Not Set

Medium (Medium)

Description

X-Frame-Options header is not included in the HTTP response to protect against 'ClickJacking' attacks.

Instances: 1

Solution

Most modern Web browsers support the X-Frame-Options HTTP header. Ensure it's set on all web pages returned by your site (if you expect the page to be framed only by pages on your server (e.g. it's part of a FRAMESET) then you'll want to use SAMEORIGIN, otherwise if you never expect the page to be framed, you should use DENY. ALLOW-FROM allows specific websites to frame the web page in supported web browsers).

Reference

CWE Id : 16

WASC Id : 15

Source ID : 3

X-Content-Type-Options Header Missing

Low (Medium)

Description

The Anti-MIME-Sniffing header X-Content-Type-Options was not set to 'nosniff'. This allows older versions of Internet Explorer and Chrome to perform MIME-sniffing on the response body, potentially causing the response body to be interpreted and displayed as a content type other than the declared content type. Current (early 2014) and legacy versions of Firefox will use the declared content type (if one is set), rather than performing MIME-sniffing.

Instances: 61

Solution

Ensure that the application/web server sets the Content-Type header appropriately, and that it sets the X-Content-Type-Options header to 'nosniff' for all web pages.

If possible, ensure that the end user uses a standards-compliant and modern web browser that does not perform MIME-sniffing at all, or that can be directed by the web application/web server to not perform MIME-sniffing.

Other information

This issue still applies to error type pages (401, 403, 500, etc) as those pages are often still affected by injection issues, in which case there is still concern for browsers sniffing pages away from their actual content type.

At "High" threshold this scanner will not alert on client or server error responses.

Reference

CWE Id : 16

WASC Id : 15

Source ID : 3

Cookie No HttpOnly Flag

Low (Medium)

Description

A cookie has been set without the HttpOnly flag, which means that the cookie can be accessed by JavaScript. If a malicious script can be run on this page then the cookie will be accessible and can be transmitted to another site. If this is a session cookie then session hijacking may be possible.

Instances: 2

Solution

Ensure that the HttpOnly flag is set for all cookies.

Reference

CWE Id : 16

WASC Id : 13

Source ID : 3

Web Browser XSS Protection Not Enabled

Low (Medium)

Description

Web Browser XSS Protection is not enabled, or is disabled by the configuration of the 'X-XSS-Protection' HTTP response header on the web server

Instances: 39

Solution

Ensure that the web browser's XSS filter is enabled, by setting the X-XSS-Protection HTTP response header to '1'.

Other information

The X-XSS-Protection HTTP response header allows the web server to enable or disable the web browser's XSS protection mechanism. The following values would attempt to enable it:

X-XSS-Protection: 1; mode=block

X-XSS-Protection: 1; report=http://www.example.com/xss

The following values would disable it:

X-XSS-Protection: 0

The X-XSS-Protection HTTP response header is currently supported on Internet Explorer, Chrome and Safari (WebKit).

Note that this alert is only raised if the response body could potentially contain an XSS payload (with a text-based content type, with a non-zero length).

Reference

CWE Id : 933

WASC Id : 14

Source ID : 3

Content-Type Header Missing

Low (Medium)

Description

The Content-Type header was either missing or empty.

Instances: 5

Solution

Ensure each page is setting the specific and appropriate content-type value for the content being delivered.

Reference

CWE Id : 345

WASC Id : 12

Source ID : 3

X-Content-Type-Options Header Missing

Low (Medium)

Description

The Anti-MIME-Sniffing header X-Content-Type-Options was not set to 'nosniff'. This allows older versions of Internet Explorer and Chrome to perform MIME-sniffing on the response body, potentially causing the response body to be interpreted and displayed as a content type other than the declared content type. Current (early 2014) and legacy versions of Firefox will use the declared content type (if one is set), rather than performing MIME-sniffing.

Instances: 2

Solution

Ensure that the application/web server sets the Content-Type header appropriately, and that it sets the X-Content-Type-Options header to 'nosniff' for all web pages.

If possible, ensure that the end user uses a standards-compliant and modern web browser that does not perform MIME-sniffing at all, or that can be directed by the web application/web server to not perform MIME-sniffing.

Other information

This issue still applies to error type pages (401, 403, 500, etc) as those pages are often still affected by injection issues, in which case there is still concern for browsers sniffing pages away from their actual content type.

At "High" threshold this scanner will not alert on client or server error responses.

Reference

CWE Id : 16

WASC Id : 15

Source ID : 3

Web Browser XSS Protection Not Enabled

Low (Medium)

Description

Web Browser XSS Protection is not enabled, or is disabled by the configuration of the 'X-XSS-Protection' HTTP response header on the web server

Instances: 1

Solution

Ensure that the web browser's XSS filter is enabled, by setting the X-XSS-Protection HTTP response header to '1'.

Other information

The X-XSS-Protection HTTP response header allows the web server to enable or disable the web browser's XSS protection mechanism. The following values would attempt to enable it:

X-XSS-Protection: 1; mode=block

X-XSS-Protection: 1; report=http://www.example.com/xss

The following values would disable it:

X-XSS-Protection: 0

The X-XSS-Protection HTTP response header is currently supported on Internet Explorer, Chrome and Safari (WebKit).

Note that this alert is only raised if the response body could potentially contain an XSS payload (with a text-based content type, with a non-zero length).

Reference

CWE Id : 933

WASC Id : 14

Source ID : 3