Repeat macro in C?
Tags: c, programming, cpp
Published: 2023-04-30 12:52:31

Sometimes we want to repeat something at compile time using C, although this sounds difficult to elaborate.
Trying I managed to elaborate the following example:

```c
#include <stdio.h>

#define REPEAT_1(FN) FN(0)
#define REPEAT_2(FN) REPEAT_1(FN) FN(1)
#define REPEAT_3(FN) REPEAT_2(FN) FN(2)
#define REPEAT_4(FN) REPEAT_3(FN) FN(3)
#define REPEAT_5(FN) REPEAT_4(FN) FN(4)
#define REPEAT_6(FN) REPEAT_5(FN) FN(5)
#define REPEAT_7(FN) REPEAT_6(FN) FN(6)
#define REPEAT_8(FN) REPEAT_7(FN) FN(7)
#define REPEAT_9(FN) REPEAT_8(FN) FN(8)
#define REPEAT_10(FN) REPEAT_9(FN) FN(9)

#define REPEAT(FN, N) REPEAT_##N(FN)

#define PRINTF(N) printf("%d\n", N);

int main() {
    REPEAT(PRINTF, 10)
}
```

We will find the following output:

```
0
1
2
3
4
5
6
7
8
9
```
The main macro is called REPEAT, which takes a function/macro name and a loop count as its arguments. It then generates a call to one of the other macros (REPEAT_1, REPEAT_2, etc.) depending on the loop count.

Each of the REPEAT_X macros generates code for a loop that calls the specified function X times with different arguments. For example, REPEAT_5 generates a loop that calls the function 5 times with the arguments 0 through 4.

We can see the PRINTF macro calling printf with an integer argument. It then calls REPEAT with PRINTF and a loop count of 10, which generates code that calls printf 10 times with the arguments 0 through 9.

This will generate the assembly output we expect.

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rd3pifznisgbzmn1gt04.png)

We will need to specify more REPEAT macros if we need repeating more than 10 times. 

Here's the REPEAT macro which can repeat 100 times:

```c
#define REPEAT_1(FN) FN(0)
#define REPEAT_2(FN) REPEAT_1(FN) FN(1)
#define REPEAT_3(FN) REPEAT_2(FN) FN(2)
#define REPEAT_4(FN) REPEAT_3(FN) FN(3)
#define REPEAT_5(FN) REPEAT_4(FN) FN(4)
#define REPEAT_6(FN) REPEAT_5(FN) FN(5)
#define REPEAT_7(FN) REPEAT_6(FN) FN(6)
#define REPEAT_8(FN) REPEAT_7(FN) FN(7)
#define REPEAT_9(FN) REPEAT_8(FN) FN(8)
#define REPEAT_10(FN) REPEAT_9(FN) FN(9)
#define REPEAT_11(FN) REPEAT_10(FN) FN(10)
#define REPEAT_12(FN) REPEAT_11(FN) FN(11)
#define REPEAT_13(FN) REPEAT_12(FN) FN(12)
#define REPEAT_14(FN) REPEAT_13(FN) FN(13)
#define REPEAT_15(FN) REPEAT_14(FN) FN(14)
#define REPEAT_16(FN) REPEAT_15(FN) FN(15)
#define REPEAT_17(FN) REPEAT_16(FN) FN(16)
#define REPEAT_18(FN) REPEAT_17(FN) FN(17)
#define REPEAT_19(FN) REPEAT_18(FN) FN(18)
#define REPEAT_20(FN) REPEAT_19(FN) FN(19)
#define REPEAT_21(FN) REPEAT_20(FN) FN(20)
#define REPEAT_22(FN) REPEAT_21(FN) FN(21)
#define REPEAT_23(FN) REPEAT_22(FN) FN(22)
#define REPEAT_24(FN) REPEAT_23(FN) FN(23)
#define REPEAT_25(FN) REPEAT_24(FN) FN(24)
#define REPEAT_26(FN) REPEAT_25(FN) FN(25)
#define REPEAT_27(FN) REPEAT_26(FN) FN(26)
#define REPEAT_28(FN) REPEAT_27(FN) FN(27)
#define REPEAT_29(FN) REPEAT_28(FN) FN(28)
#define REPEAT_30(FN) REPEAT_29(FN) FN(29)
#define REPEAT_31(FN) REPEAT_30(FN) FN(30)
#define REPEAT_32(FN) REPEAT_31(FN) FN(31)
#define REPEAT_33(FN) REPEAT_32(FN) FN(32)
#define REPEAT_34(FN) REPEAT_33(FN) FN(33)
#define REPEAT_35(FN) REPEAT_34(FN) FN(34)
#define REPEAT_36(FN) REPEAT_35(FN) FN(35)
#define REPEAT_37(FN) REPEAT_36(FN) FN(36)
#define REPEAT_38(FN) REPEAT_37(FN) FN(37)
#define REPEAT_39(FN) REPEAT_38(FN) FN(38)
#define REPEAT_40(FN) REPEAT_39(FN) FN(39)
#define REPEAT_41(FN) REPEAT_40(FN) FN(40)
#define REPEAT_42(FN) REPEAT_41(FN) FN(41)
#define REPEAT_43(FN) REPEAT_42(FN) FN(42)
#define REPEAT_44(FN) REPEAT_43(FN) FN(43)
#define REPEAT_45(FN) REPEAT_44(FN) FN(44)
#define REPEAT_46(FN) REPEAT_45(FN) FN(45)
#define REPEAT_47(FN) REPEAT_46(FN) FN(46)
#define REPEAT_48(FN) REPEAT_47(FN) FN(47)
#define REPEAT_49(FN) REPEAT_48(FN) FN(48)
#define REPEAT_50(FN) REPEAT_49(FN) FN(49)
#define REPEAT_51(FN) REPEAT_50(FN) FN(50)
#define REPEAT_52(FN) REPEAT_51(FN) FN(51)
#define REPEAT_53(FN) REPEAT_52(FN) FN(52)
#define REPEAT_54(FN) REPEAT_53(FN) FN(53)
#define REPEAT_55(FN) REPEAT_54(FN) FN(54)
#define REPEAT_56(FN) REPEAT_55(FN) FN(55)
#define REPEAT_57(FN) REPEAT_56(FN) FN(56)
#define REPEAT_58(FN) REPEAT_57(FN) FN(57)
#define REPEAT_59(FN) REPEAT_58(FN) FN(58)
#define REPEAT_60(FN) REPEAT_59(FN) FN(59)
#define REPEAT_61(FN) REPEAT_60(FN) FN(60)
#define REPEAT_62(FN) REPEAT_61(FN) FN(61)
#define REPEAT_63(FN) REPEAT_62(FN) FN(62)
#define REPEAT_64(FN) REPEAT_63(FN) FN(63)
#define REPEAT_65(FN) REPEAT_64(FN) FN(64)
#define REPEAT_66(FN) REPEAT_65(FN) FN(65)
#define REPEAT_67(FN) REPEAT_66(FN) FN(66)
#define REPEAT_68(FN) REPEAT_67(FN) FN(67)
#define REPEAT_69(FN) REPEAT_68(FN) FN(68)
#define REPEAT_70(FN) REPEAT_69(FN) FN(69)
#define REPEAT_71(FN) REPEAT_70(FN) FN(70)
#define REPEAT_72(FN) REPEAT_71(FN) FN(71)
#define REPEAT_73(FN) REPEAT_72(FN) FN(72)
#define REPEAT_74(FN) REPEAT_73(FN) FN(73)
#define REPEAT_75(FN) REPEAT_74(FN) FN(74)
#define REPEAT_76(FN) REPEAT_75(FN) FN(75)
#define REPEAT_77(FN) REPEAT_76(FN) FN(76)
#define REPEAT_78(FN) REPEAT_77(FN) FN(77)
#define REPEAT_79(FN) REPEAT_78(FN) FN(78)
#define REPEAT_80(FN) REPEAT_79(FN) FN(79)
#define REPEAT_81(FN) REPEAT_80(FN) FN(80)
#define REPEAT_82(FN) REPEAT_81(FN) FN(81)
#define REPEAT_83(FN) REPEAT_82(FN) FN(82)
#define REPEAT_84(FN) REPEAT_83(FN) FN(83)
#define REPEAT_85(FN) REPEAT_84(FN) FN(84)
#define REPEAT_86(FN) REPEAT_85(FN) FN(85)
#define REPEAT_87(FN) REPEAT_86(FN) FN(86)
#define REPEAT_88(FN) REPEAT_87(FN) FN(87)
#define REPEAT_89(FN) REPEAT_88(FN) FN(88)
#define REPEAT_90(FN) REPEAT_89(FN) FN(89)
#define REPEAT_91(FN) REPEAT_90(FN) FN(90)
#define REPEAT_92(FN) REPEAT_91(FN) FN(91)
#define REPEAT_93(FN) REPEAT_92(FN) FN(92)
#define REPEAT_94(FN) REPEAT_93(FN) FN(93)
#define REPEAT_95(FN) REPEAT_94(FN) FN(94)
#define REPEAT_96(FN) REPEAT_95(FN) FN(95)
#define REPEAT_97(FN) REPEAT_96(FN) FN(96)
#define REPEAT_98(FN) REPEAT_97(FN) FN(97)
#define REPEAT_99(FN) REPEAT_98(FN) FN(98)
#define REPEAT_100(FN) REPEAT_99(FN) FN(99)

#define REPEAT(FN, N) REPEAT_##N(FN)
```