The problem is your initialization using DockStyle.Top:
CustomControl control = new CustomControl(labelCaption: "First control caption");
control.Dock = DockStyle.Top;
CustomControl control2 = new CustomControl(labelCaption: "second control caption");
control2.Dock = DockStyle.Top;
They're going to overlay each other this way. Instead of using DockStyle, use positioning attributes:
control.Top = 0;
control2.Top = control.Height;
That should get you where you need to go.
A great way to learn about how to do this well is to look at the code the designer generates. Do this by hand in the designer, then look at the generated code, and it will help you generalize how to do the positioning in code yourself in the future.
Edit based on your comment:
You can use a FlowLayoutPanel and set a FlowBreak after each:
flowLayoutPanel.Controls.Add(control);
flowLayoutPanel.Controls.Add(control2);
flowLayoutPanel.SetFlowBreak(control, true);
flowLayoutPanel.SetFlowBreak(control2, true);