Hacktoberfest 2026:メンテナが10月に向けて印を付けた、オープンで初心者向けの issue。 Hacktoberfest の issue を見る

Go: go/comparison-of-identical-expressions false positive when a variable is reassigned in a range loop (go-all 8.0.0)

クローズ
#22,770 コメント 1 件 リアクション 0 件 担当者 0 名 GitHub で見る

メンテナーはふだん 1 日以内に返信

まだ誰も着手していません。

評価

難易度
4/5
見積もり時間
3〜5日
初心者へのやさしさ
54/100
issue の種類
バグ
明瞭さ
明確に書かれている
活発さ
活発
技術スタック
go
領域
testing-qa

調査の方向性

Start by reproducing the false positive with the Go samples in the issue and the two versions of CompareIdenticalValues.ql; compare results with go-all 7.3.2 and 8.0.0. Investigate how the range-loop CFG handles assignments that flow past the loop, and check whether related data-flow queries are affected. Done when the range-loop comparison is no longer reported while the issue’s other cases behave as expected.

索引モデルが issue の本文から書いたものです。

説明

Description of the false positive

Since codeql/go-queries 1.6.12 (with codeql/go-all 8.0.0), go/comparison-of-identical-expressions reports a comparison between a variable and the value it was initialised from, even though the variable may be reassigned inside a range loop between the two. With codeql/go-queries 1.6.11 (codeql/go-all 7.3.2), the same database gives no result.

The trigger is the range loop. The same assignment in a plain if or in a three-clause for loop is not reported. It looks related to the CFG rewrite in go-all 8.0.0, whose changelog mentions range statements. If assignments in a range body don't reach the code after the loop, other data-flow queries might be affected as well. I have only checked this query.

Code samples or links to source code

package repro

// Reported (line "if n == c"): n may be raised inside the range loop.
func Settle(c int, xs []int) int {
	for {
		n := c
		for _, x := range xs {
			if x > n {
				n = x
			}
		}
		if n == c { // <- "This expression compares an expression to itself."
			break
		}
		c = n
	}
	return c
}

// Also reported: unconditional assignment in a range loop.
func VariantD(c int, xs []int) int {
	n := c
	for _, x := range xs {
		n = x
	}
	if n == c { // <- reported
		return 0
	}
	return n
}

// Not reported: the same assignment in a three-clause loop.
func VariantB(c int, xs []int) int {
	n := c
	for i := 0; i < len(xs); i++ {
		if xs[i] > n {
			n = xs[i]
		}
	}
	if n == c {
		return 0
	}
	return n
}

To reproduce (CodeQL CLI 2.27.1, macOS arm64, Go 1.25.13). --no-tracing is used only because this machine has no Rosetta for the tracer.

codeql database create db --language=go --source-root src --build-mode=autobuild --no-tracing
codeql database analyze db codeql/[email protected]:RedundantCode/CompareIdenticalValues.ql --format=sarif-latest --output=a.sarif --rerun
codeql database analyze db codeql/[email protected]:RedundantCode/CompareIdenticalValues.ql --format=sarif-latest --output=b.sarif --rerun
  • a.sarif, go-queries 1.6.11 / go-all 7.3.2: 0 results.
  • b.sarif, go-queries 1.6.12 / go-all 8.0.0: 3 results: Settle, VariantD, and a third range-loop variant without the outer loop.

Without --rerun, the second command silently reuses the first command's cached results: its SARIF reports go-queries 1.6.11 and 0 results. This may be worth a look separately.

The same comparison is reported in real code here: https://github.com/gomaja/go-asn1/blob/2e83d89af0dc815fc1e0a589691032aa069153bc/runtime/ber/named_bit_size.go#L43. In that code, next starts as candidate and can be raised inside the range loop over the permitted intervals.

主要言語
CodeQL
スター
10.2k
フォーク
2.1k
平均マージ
2日 15時間
マージ済み PR(30日)
153

環境構築

Codespaces で開く

このプロジェクトの開発コンテナを、あなたの GitHub アカウントでブラウザ上に起動します。

はじめの一歩

  1. issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
  2. 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
  3. リポジトリをフォークし、ブランチを切って変更します。
  4. issue 番号を参照したプルリクエストを送ります。

github/codeql のほかの issue

github/codeql の issue をすべて見る

似ている issue

Testing & QA の issue をもっと見る

新しい issue をメールで受け取る

初心者向けの GitHub issue を短くまとめたダイジェスト。