#include <stdint.h> #include <stddef.h> /** * Name: CRC-32/MPEG-2 x32+x26+x23+x22+x16+x12+x11+x10+x8+x7+x5+x4+x2+x+1 * Poly: 0x4C11DB7 * Init: 0xFFFFFFF * Refin: False * Refout: False * Xorout: 0x0000000 * Note: */ uint32_t crc32(const uint8_t *data, size_t length) { uint8_t i; uint32_t crc = 0xffffffff; // Initial value while (length--) { crc ^= (uint32_t)(*data++) << 24; for (i = 0; i < 8; ++i) { if (crc & 0x80000000) crc = (crc << 1) ^ 0x04C11DB7; else crc <<= 1; } } return crc; }
For this code, the Os/Oz option results in generating larger code than O3.
https://godbolt.org/z/MEqqK1q5T
Section size for -Os options
```
| .text | .data | .bss | .rodata |
| 44(+0) | 0(+0) | 0(+0) | 1024(+0) |
```Section size for -O3 options```
| 104(+0) | 0(+0) | 0(+0) | 0(+0) |
The behavior is normal on gcc 10.3.1.
Hi lei cao !
The code (.text segment) is definitely smaller with -Os then -O3, but GCC 15.2 uses/places some read-only variables into the .rodata segment. I don't have GCC 10.3.1 here but you could test which optimization option does this.
You can invoke GCC following to see enabled/disabled optimization options at the specific level:
For -Os:
$ arm-none-eabi-gcc --help=optimizers -Q -Os The following options control optimizations: --param=lto-partition-locality-cloning= maximal -O<number> -Ofast -Og -Os -Oz -faggressive-loop-optimizations [enabled] -falign-functions [disabled] -falign-functions= -falign-jumps [disabled] -falign-jumps= -falign-labels [disabled] -falign-labels= -falign-loops [disabled] -falign-loops= -fallocation-dce [enabled] -fallow-store-data-races [disabled] -fassociative-math [disabled] -fassume-sane-operators-new-delete [available in C++, ObjC++] -fasynchronous-unwind-tables [disabled] -fauto-inc-dec [enabled] -favoid-store-forwarding [disabled] -fbit-tests [enabled] -fbranch-count-reg [enabled] -fbranch-probabilities [disabled] -fcaller-saves [enabled] -fcode-hoisting [enabled] -fcombine-stack-adjustments [enabled] -fcompare-elim [enabled] -fconserve-stack [disabled] -fcprop-registers [enabled] -fcrossjumping [enabled] -fcse-follow-jumps [enabled] -fcx-fortran-rules [disabled] -fcx-limited-range [disabled] -fdce [enabled] -fdefer-pop [enabled] -fdelayed-branch [disabled] -fdelete-dead-exceptions [disabled] -fdelete-null-pointer-checks -fdevirtualize [enabled] -fdevirtualize-speculatively [enabled] -fdse [enabled] -fearly-inlining [enabled] -fexceptions [available in D, Modula-2] -fexcess-precision=[fast|standard|16] [default] -fexpensive-optimizations [enabled] -fext-dce [enabled] -ffast-math -ffinite-loops [disabled] -ffinite-math-only [disabled] -ffloat-store [disabled] -ffold-mem-offsets [enabled] -ffold-simple-inlines [available in C++, ObjC++] -fforward-propagate [enabled] -ffp-contract=[off|on|fast] fast -ffp-int-builtin-inexact [enabled] -ffunction-cse [enabled] -fgcse [enabled] -fgcse-after-reload [disabled] -fgcse-las [disabled] -fgcse-lm [enabled] -fgcse-sm [disabled] -fgraphite [disabled] -fgraphite-identity [disabled] -fguess-branch-probability [enabled] -fhandle-exceptions -fexceptions -fhardcfr-check-exceptions -fhardcfr-check-noreturn-calls=[always|no-xthrow|nothrow|never] [default] -fhardcfr-check-returning-calls -fhardcfr-skip-leaf [disabled] -fharden-compares [disabled] -fharden-conditional-branches [disabled] -fharden-control-flow-redundancy [disabled] -fhoist-adjacent-loads [enabled] -fif-conversion [enabled] -fif-conversion2 [enabled] -findirect-inlining [enabled] -finline [enabled] -finline-atomics [enabled] -finline-functions [enabled] -finline-functions-called-once [enabled] -finline-small-functions [enabled] -finline-stringops [disabled] -finline-stringops= [default] -fipa-bit-cp [enabled] -fipa-cp [enabled] -fipa-cp-clone [disabled] -fipa-icf [enabled] -fipa-icf-functions [enabled] -fipa-icf-variables [enabled] -fipa-modref [enabled] -fipa-profile [enabled] -fipa-pta [disabled] -fipa-pure-const [enabled] -fipa-ra [enabled] -fipa-reference [enabled] -fipa-reference-addressable [enabled] -fipa-reorder-for-locality [disabled] -fipa-sra [enabled] -fipa-stack-alignment [enabled] -fipa-strict-aliasing [enabled] -fipa-vrp [enabled] -fira-algorithm=[CB|priority] CB -fira-hoist-pressure [enabled] -fira-loop-pressure [disabled] -fira-region=[one|all|mixed] one -fira-share-save-slots [enabled] -fira-share-spill-slots [enabled] -fisolate-erroneous-paths-attribute [disabled] -fisolate-erroneous-paths-dereference [enabled] -fivopts [enabled] -fjump-tables [enabled] -fkeep-gc-roots-live [disabled] -flate-combine-instructions [enabled] -flifetime-dse [enabled] -flifetime-dse=<0,2> 2 -flimit-function-alignment [disabled] -flive-patching -flive-patching=inline-clone -flive-patching=[inline-only-static|inline-clone] [default] -flive-range-shrinkage [disabled] -floop-interchange [disabled] -floop-nest-optimize [disabled] -floop-parallelize-all [disabled] -floop-unroll-and-jam [disabled] -flra-remat [enabled] -fmalloc-dce [enabled] -fmalloc-dce=<0,2> 0 -fmath-errno [enabled] -fmin-function-alignment= 0 -fmodulo-sched [disabled] -fmodulo-sched-allow-regmoves [disabled] -fmove-loop-invariants [enabled] -fmove-loop-stores [enabled] -fno-inline-stringops [enabled] -fnon-call-exceptions [disabled] -fnothrow-opt [available in C++, ObjC++] -fomit-frame-pointer [enabled] -fopenmp-target-simd-clone= none -fopt-info [disabled] -foptimize-crc [enabled] -foptimize-sibling-calls [enabled] -foptimize-strlen [disabled] -fpack-struct [disabled] -fpack-struct=<number> -fpartial-inlining [enabled] -fpatchable-function-entry= -fpcc-struct-return [disabled] -fpeel-loops [disabled] -fpeephole [enabled] -fpeephole2 [enabled] -fplt [enabled] -fpredictive-commoning [disabled] -fprefetch-loop-arrays -fprintf-return-value [enabled] -fprofile-partial-training [disabled] -fprofile-reorder-functions [disabled] -freciprocal-math [disabled] -free [disabled] -freg-struct-return -fpcc-struct-return -frename-registers [disabled] -freorder-blocks [enabled] -freorder-blocks-algorithm=[simple|stc] simple -freorder-blocks-and-partition [disabled] -freorder-functions [enabled] -frerun-cse-after-loop [enabled] -freschedule-modulo-scheduled-loops [disabled] -frounding-math [disabled] -frtti [available in C++, D, ObjC++] -fsave-optimization-record [disabled] -fsched-critical-path-heuristic [enabled] -fsched-dep-count-heuristic [enabled] -fsched-group-heuristic [enabled] -fsched-interblock [enabled] -fsched-last-insn-heuristic [enabled] -fsched-pressure [enabled] -fsched-rank-heuristic [enabled] -fsched-spec [enabled] -fsched-spec-insn-heuristic [enabled] -fsched-spec-load [disabled] -fsched-spec-load-dangerous [disabled] -fsched-stalled-insns [disabled] -fsched-stalled-insns-dep [enabled] -fsched-stalled-insns-dep=<number> -fsched-stalled-insns=<number> -fsched2-use-superblocks [disabled] -fschedule-fusion [disabled] -fschedule-insns [disabled] -fschedule-insns2 [enabled] -fsection-anchors [enabled] -fsel-sched-pipelining [disabled] -fsel-sched-pipelining-outer-loops [disabled] -fsel-sched-reschedule-pipelined [disabled] -fselective-scheduling [disabled] -fselective-scheduling2 [disabled] -fsemantic-interposition [enabled] -fshort-enums [disabled] -fshort-wchar [disabled] -fshrink-wrap [enabled] -fshrink-wrap-separate [enabled] -fsignaling-nans [disabled] -fsigned-zeros [enabled] -fsimd-cost-model=[unlimited|dynamic|cheap|very-cheap] unlimited -fsingle-precision-constant [disabled] -fsplit-ivs-in-unroller [enabled] -fsplit-loops [disabled] -fsplit-paths [disabled] -fsplit-wide-types [enabled] -fsplit-wide-types-early [disabled] -fssa-backprop [enabled] -fssa-phiopt [enabled] -fstack-check=[no|generic|specific] -fstack-clash-protection [disabled] -fstack-protector [disabled] -fstack-protector-all [disabled] -fstack-protector-explicit [disabled] -fstack-protector-strong [disabled] -fstack-reuse=[all|named_vars|none] all -fstdarg-opt [enabled] -fstore-merging [enabled] -fstrict-aliasing [enabled] -fstrict-enums [available in C++, ObjC++] -fstrict-volatile-bitfields [enabled] -fthread-jumps [enabled] -fno-threadsafe-statics [available in C++, ObjC++] -ftoplevel-reorder [enabled] -ftracer [disabled] -ftrapping-math [enabled] -ftrapv [disabled] -ftree-bit-ccp [enabled] -ftree-builtin-call-dce [enabled] -ftree-ccp [enabled] -ftree-ch [enabled] -ftree-coalesce-vars [enabled] -ftree-copy-prop [enabled] -ftree-cselim [disabled] -ftree-dce [enabled] -ftree-dominator-opts [enabled] -ftree-dse [enabled] -ftree-forwprop [enabled] -ftree-fre [enabled] -ftree-loop-distribute-patterns [enabled] -ftree-loop-distribution [disabled] -ftree-loop-if-convert -ftree-loop-im [enabled] -ftree-loop-ivcanon [enabled] -ftree-loop-optimize [enabled] -ftree-loop-vectorize [disabled] -ftree-lrs [disabled] -ftree-parallelize-loops=<number> 1 -ftree-partial-pre [disabled] -ftree-phiprop [enabled] -ftree-pre [enabled] -ftree-pta [enabled] -ftree-reassoc [enabled] -ftree-scev-cprop [enabled] -ftree-sink [enabled] -ftree-slp-vectorize [disabled] -ftree-slsr [enabled] -ftree-sra [enabled] -ftree-switch-conversion [enabled] -ftree-tail-merge [enabled] -ftree-ter [enabled] -ftree-vectorize [disabled] -ftree-vrp [enabled] -ftrivial-auto-var-init=[uninitialized|pattern|zero] uninitialized -funconstrained-commons [disabled] -funreachable-traps [disabled] -funroll-all-loops [disabled] -funroll-completely-grow-size [disabled] -funroll-loops [disabled] -funsafe-math-optimizations [disabled] -funswitch-loops [disabled] -funwind-tables [disabled] -fvar-tracking [disabled] -fvar-tracking-assignments [disabled] -fvar-tracking-assignments-toggle [disabled] -fvar-tracking-uninit [disabled] -fvariable-expansion-in-unroller [disabled] -fvect-cost-model=[unlimited|dynamic|cheap|very-cheap] very-cheap -fversion-loops-for-strides [disabled] -fvpt [disabled] -fweb [disabled] -fwrapv [disabled] -fwrapv-pointer [disabled] -gstatement-frontiers [disabled] $
For -O3:
$ arm-none-eabi-gcc --help=optimizers -Q -O3 The following options control optimizations: --param=lto-partition-locality-cloning= maximal -O<number> -Ofast -Og -Os -Oz -faggressive-loop-optimizations [enabled] -falign-functions [enabled] -falign-functions= 4 -falign-jumps [enabled] -falign-jumps= -falign-labels [enabled] -falign-labels= -falign-loops [enabled] -falign-loops= -fallocation-dce [enabled] -fallow-store-data-races [disabled] -fassociative-math [disabled] -fassume-sane-operators-new-delete [available in C++, ObjC++] -fasynchronous-unwind-tables [disabled] -fauto-inc-dec [enabled] -favoid-store-forwarding [disabled] -fbit-tests [enabled] -fbranch-count-reg [enabled] -fbranch-probabilities [disabled] -fcaller-saves [enabled] -fcode-hoisting [enabled] -fcombine-stack-adjustments [enabled] -fcompare-elim [enabled] -fconserve-stack [disabled] -fcprop-registers [enabled] -fcrossjumping [enabled] -fcse-follow-jumps [enabled] -fcx-fortran-rules [disabled] -fcx-limited-range [disabled] -fdce [enabled] -fdefer-pop [enabled] -fdelayed-branch [disabled] -fdelete-dead-exceptions [disabled] -fdelete-null-pointer-checks -fdevirtualize [enabled] -fdevirtualize-speculatively [enabled] -fdse [enabled] -fearly-inlining [enabled] -fexceptions [available in D, Modula-2] -fexcess-precision=[fast|standard|16] [default] -fexpensive-optimizations [enabled] -fext-dce [enabled] -ffast-math -ffinite-loops [disabled] -ffinite-math-only [disabled] -ffloat-store [disabled] -ffold-mem-offsets [enabled] -ffold-simple-inlines [available in C++, ObjC++] -fforward-propagate [enabled] -ffp-contract=[off|on|fast] fast -ffp-int-builtin-inexact [enabled] -ffunction-cse [enabled] -fgcse [enabled] -fgcse-after-reload [enabled] -fgcse-las [disabled] -fgcse-lm [enabled] -fgcse-sm [disabled] -fgraphite [disabled] -fgraphite-identity [disabled] -fguess-branch-probability [enabled] -fhandle-exceptions -fexceptions -fhardcfr-check-exceptions -fhardcfr-check-noreturn-calls=[always|no-xthrow|nothrow|never] [default] -fhardcfr-check-returning-calls -fhardcfr-skip-leaf [disabled] -fharden-compares [disabled] -fharden-conditional-branches [disabled] -fharden-control-flow-redundancy [disabled] -fhoist-adjacent-loads [enabled] -fif-conversion [enabled] -fif-conversion2 [enabled] -findirect-inlining [enabled] -finline [enabled] -finline-atomics [enabled] -finline-functions [enabled] -finline-functions-called-once [enabled] -finline-small-functions [enabled] -finline-stringops [disabled] -finline-stringops= [default] -fipa-bit-cp [enabled] -fipa-cp [enabled] -fipa-cp-clone [enabled] -fipa-icf [enabled] -fipa-icf-functions [enabled] -fipa-icf-variables [enabled] -fipa-modref [enabled] -fipa-profile [enabled] -fipa-pta [disabled] -fipa-pure-const [enabled] -fipa-ra [enabled] -fipa-reference [enabled] -fipa-reference-addressable [enabled] -fipa-reorder-for-locality [disabled] -fipa-sra [enabled] -fipa-stack-alignment [enabled] -fipa-strict-aliasing [enabled] -fipa-vrp [enabled] -fira-algorithm=[CB|priority] CB -fira-hoist-pressure [enabled] -fira-loop-pressure [disabled] -fira-region=[one|all|mixed] one -fira-share-save-slots [enabled] -fira-share-spill-slots [enabled] -fisolate-erroneous-paths-attribute [disabled] -fisolate-erroneous-paths-dereference [enabled] -fivopts [enabled] -fjump-tables [enabled] -fkeep-gc-roots-live [disabled] -flate-combine-instructions [enabled] -flifetime-dse [enabled] -flifetime-dse=<0,2> 2 -flimit-function-alignment [disabled] -flive-patching -flive-patching=inline-clone -flive-patching=[inline-only-static|inline-clone] [default] -flive-range-shrinkage [disabled] -floop-interchange [enabled] -floop-nest-optimize [disabled] -floop-parallelize-all [disabled] -floop-unroll-and-jam [enabled] -flra-remat [enabled] -fmalloc-dce [enabled] -fmalloc-dce=<0,2> 0 -fmath-errno [enabled] -fmin-function-alignment= 0 -fmodulo-sched [disabled] -fmodulo-sched-allow-regmoves [disabled] -fmove-loop-invariants [enabled] -fmove-loop-stores [enabled] -fno-inline-stringops [enabled] -fnon-call-exceptions [disabled] -fnothrow-opt [available in C++, ObjC++] -fomit-frame-pointer [enabled] -fopenmp-target-simd-clone= nohost -fopt-info [disabled] -foptimize-crc [enabled] -foptimize-sibling-calls [enabled] -foptimize-strlen [enabled] -fpack-struct [disabled] -fpack-struct=<number> -fpartial-inlining [enabled] -fpatchable-function-entry= -fpcc-struct-return [disabled] -fpeel-loops [enabled] -fpeephole [enabled] -fpeephole2 [enabled] -fplt [enabled] -fpredictive-commoning [enabled] -fprefetch-loop-arrays -fprintf-return-value [enabled] -fprofile-partial-training [disabled] -fprofile-reorder-functions [disabled] -freciprocal-math [disabled] -free [disabled] -freg-struct-return -fpcc-struct-return -frename-registers [disabled] -freorder-blocks [enabled] -freorder-blocks-algorithm=[simple|stc] stc -freorder-blocks-and-partition [disabled] -freorder-functions [enabled] -frerun-cse-after-loop [enabled] -freschedule-modulo-scheduled-loops [disabled] -frounding-math [disabled] -frtti [available in C++, D, ObjC++] -fsave-optimization-record [disabled] -fsched-critical-path-heuristic [enabled] -fsched-dep-count-heuristic [enabled] -fsched-group-heuristic [enabled] -fsched-interblock [enabled] -fsched-last-insn-heuristic [enabled] -fsched-pressure [enabled] -fsched-rank-heuristic [enabled] -fsched-spec [enabled] -fsched-spec-insn-heuristic [enabled] -fsched-spec-load [disabled] -fsched-spec-load-dangerous [disabled] -fsched-stalled-insns [disabled] -fsched-stalled-insns-dep [enabled] -fsched-stalled-insns-dep=<number> -fsched-stalled-insns=<number> -fsched2-use-superblocks [disabled] -fschedule-fusion [disabled] -fschedule-insns [enabled] -fschedule-insns2 [enabled] -fsection-anchors [enabled] -fsel-sched-pipelining [disabled] -fsel-sched-pipelining-outer-loops [disabled] -fsel-sched-reschedule-pipelined [disabled] -fselective-scheduling [disabled] -fselective-scheduling2 [disabled] -fsemantic-interposition [enabled] -fshort-enums [disabled] -fshort-wchar [disabled] -fshrink-wrap [enabled] -fshrink-wrap-separate [enabled] -fsignaling-nans [disabled] -fsigned-zeros [enabled] -fsimd-cost-model=[unlimited|dynamic|cheap|very-cheap] unlimited -fsingle-precision-constant [disabled] -fsplit-ivs-in-unroller [enabled] -fsplit-loops [enabled] -fsplit-paths [enabled] -fsplit-wide-types [enabled] -fsplit-wide-types-early [disabled] -fssa-backprop [enabled] -fssa-phiopt [enabled] -fstack-check=[no|generic|specific] -fstack-clash-protection [disabled] -fstack-protector [disabled] -fstack-protector-all [disabled] -fstack-protector-explicit [disabled] -fstack-protector-strong [disabled] -fstack-reuse=[all|named_vars|none] all -fstdarg-opt [enabled] -fstore-merging [enabled] -fstrict-aliasing [enabled] -fstrict-enums [available in C++, ObjC++] -fstrict-volatile-bitfields [enabled] -fthread-jumps [enabled] -fno-threadsafe-statics [available in C++, ObjC++] -ftoplevel-reorder [enabled] -ftracer [disabled] -ftrapping-math [enabled] -ftrapv [disabled] -ftree-bit-ccp [enabled] -ftree-builtin-call-dce [enabled] -ftree-ccp [enabled] -ftree-ch [enabled] -ftree-coalesce-vars [enabled] -ftree-copy-prop [enabled] -ftree-cselim [disabled] -ftree-dce [enabled] -ftree-dominator-opts [enabled] -ftree-dse [enabled] -ftree-forwprop [enabled] -ftree-fre [enabled] -ftree-loop-distribute-patterns [enabled] -ftree-loop-distribution [enabled] -ftree-loop-if-convert -ftree-loop-im [enabled] -ftree-loop-ivcanon [enabled] -ftree-loop-optimize [enabled] -ftree-loop-vectorize [enabled] -ftree-lrs [disabled] -ftree-parallelize-loops=<number> 1 -ftree-partial-pre [enabled] -ftree-phiprop [enabled] -ftree-pre [enabled] -ftree-pta [enabled] -ftree-reassoc [enabled] -ftree-scev-cprop [enabled] -ftree-sink [enabled] -ftree-slp-vectorize [enabled] -ftree-slsr [enabled] -ftree-sra [enabled] -ftree-switch-conversion [enabled] -ftree-tail-merge [enabled] -ftree-ter [enabled] -ftree-vectorize [disabled] -ftree-vrp [enabled] -ftrivial-auto-var-init=[uninitialized|pattern|zero] uninitialized -funconstrained-commons [disabled] -funreachable-traps [disabled] -funroll-all-loops [disabled] -funroll-completely-grow-size [enabled] -funroll-loops [disabled] -funsafe-math-optimizations [disabled] -funswitch-loops [enabled] -funwind-tables [disabled] -fvar-tracking [disabled] -fvar-tracking-assignments [disabled] -fvar-tracking-assignments-toggle [disabled] -fvar-tracking-uninit [disabled] -fvariable-expansion-in-unroller [disabled] -fvect-cost-model=[unlimited|dynamic|cheap|very-cheap] dynamic -fversion-loops-for-strides [enabled] -fvpt [disabled] -fweb [disabled] -fwrapv [disabled] -fwrapv-pointer [disabled] -gstatement-frontiers [disabled] $
Just compare the output to narrow down the issue and feel free to open a bug report at the GCC bugtracker.
I think it should be this option: -foptimize-crc
The Docs:
-foptimize-crc
Detect loops calculating CRC (performing polynomial long division) and replace them with a faster implementation. Detect 8, 16, 32, and 64 bit CRC, with a constant polynomial without the leading 1 bit, for both bit-forward and bit-reversed cases. If the target supports a CRC instruction and the polynomial used in the source code matches the polynomial used in the CRC instruction, generate that CRC instruction. Otherwise, if the target supports a carry-less-multiplication instruction, generate CRC using it; otherwise generate table-based CRC.
Enabled by default at and higher. -O2
When i use `-Os -fno-optimize-crc`, code size (.text + .rodata) become normal.