gma power: Allow to explicitly enable DDI/Aux power

We used to enable power for DP-aux channels quite implicitly by faking
configs that use a specific port.  As Tiger Lake requires us to enable
a DDI port's power late during the modesetting sequence,  we introduce
a new API for such cases, and also use it for the DP-aux case.

Tested on HSW, and BXT & CFL where we enable PW2 explicitly now.

Change-Id: I1fd6348ff4855557166495613c6a181f85a818f4
Signed-off-by: Nico Huber <nico.huber@secunet.com>
Reviewed-on: https://review.sourcearcade.org/c/libgfxinit/+/461
Tested-by: Nico Huber <nico.h@gmx.de>
Reviewed-by: Angel Pons <th3fanbus@gmail.com>
diff --git a/common/broxton/hw-gfx-gma-power_and_clocks.adb b/common/broxton/hw-gfx-gma-power_and_clocks.adb
index e719ba5..279071a 100644
--- a/common/broxton/hw-gfx-gma-power_and_clocks.adb
+++ b/common/broxton/hw-gfx-gma-power_and_clocks.adb
@@ -192,6 +192,16 @@
       end loop;
    end Power_Set_To;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      case Port is
+         when eDP                         => PD_On (DDI_A);
+         when DP1 | HDMI1 | DP2 | HDMI2   => PW_On (PW2); PD_On (DDI_BC);
+         when others                      => null;
+      end case;
+      Success := True;
+   end Power_Up;
+
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is
    begin
       for PD in Dynamic_Domain loop
diff --git a/common/broxton/hw-gfx-gma-power_and_clocks.ads b/common/broxton/hw-gfx-gma-power_and_clocks.ads
index 36b145c..d881075 100644
--- a/common/broxton/hw-gfx-gma-power_and_clocks.ads
+++ b/common/broxton/hw-gfx-gma-power_and_clocks.ads
@@ -32,6 +32,7 @@
    procedure Enable_CDClk;
 
    procedure Power_Set_To (Configs : Pipe_Configs);
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs);
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs);
 
diff --git a/common/g45/hw-gfx-gma-power_and_clocks.adb b/common/g45/hw-gfx-gma-power_and_clocks.adb
index 0ecf09b..c0bb683 100644
--- a/common/g45/hw-gfx-gma-power_and_clocks.adb
+++ b/common/g45/hw-gfx-gma-power_and_clocks.adb
@@ -151,4 +151,9 @@
       CDClk_Switch := False;
    end Limit_Dotclocks;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      Success := True;
+   end Power_Up;
+
 end HW.GFX.GMA.Power_And_Clocks;
diff --git a/common/g45/hw-gfx-gma-power_and_clocks.ads b/common/g45/hw-gfx-gma-power_and_clocks.ads
index 313239b..eee99d0 100644
--- a/common/g45/hw-gfx-gma-power_and_clocks.ads
+++ b/common/g45/hw-gfx-gma-power_and_clocks.ads
@@ -34,6 +34,10 @@
 
    procedure Power_Set_To (Configs : Pipe_Configs) is null;
 
+   pragma Warnings (GNATprove, Off, "unused variable ""Port""",
+                    Reason => "Needed for a common interface");
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
+   pragma Warnings (GNATprove, On, "unused variable ""Port""");
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is null;
 
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs)
diff --git a/common/haswell/hw-gfx-gma-power_and_clocks.adb b/common/haswell/hw-gfx-gma-power_and_clocks.adb
index 6a00a5f..1aea48e 100644
--- a/common/haswell/hw-gfx-gma-power_and_clocks.adb
+++ b/common/haswell/hw-gfx-gma-power_and_clocks.adb
@@ -334,6 +334,14 @@
       end if;
    end Power_Set_To;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      if Port /= eDP then
+         PDW_On;
+      end if;
+      Success := True;
+   end Power_Up;
+
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is
    begin
       if not Need_PDW (Old_Configs) and Need_PDW (New_Configs) then
diff --git a/common/haswell/hw-gfx-gma-power_and_clocks.ads b/common/haswell/hw-gfx-gma-power_and_clocks.ads
index e4f2611..f7c5abe 100644
--- a/common/haswell/hw-gfx-gma-power_and_clocks.ads
+++ b/common/haswell/hw-gfx-gma-power_and_clocks.ads
@@ -32,6 +32,7 @@
    procedure Enable_CDClk is null;
 
    procedure Power_Set_To (Configs : Pipe_Configs);
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs);
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs);
 
diff --git a/common/hw-gfx-gma-display_probing.adb b/common/hw-gfx-gma-display_probing.adb
index 491a88f..72df4ed 100644
--- a/common/hw-gfx-gma-display_probing.adb
+++ b/common/hw-gfx-gma-display_probing.adb
@@ -73,13 +73,9 @@
       for I in 1 .. 2 loop
          if Config_Helpers.To_Display_Type (Port) = DP then
             -- May need power and CDClk to read EDID
-            declare
-               Temp_Configs : Pipe_Configs := Cur_Configs;
-            begin
-               Temp_Configs (Primary).Port := Port;
-               Power_And_Clocks.Power_Up (Cur_Configs, Temp_Configs);
-               Power_And_Clocks.Enable_CDClk;
-            end;
+            Power_And_Clocks.Power_Up (Port, Success);
+            exit when not Success;
+            Power_And_Clocks.Enable_CDClk;
 
             declare
                DP_Port : constant GMA.DP_Port :=
@@ -134,7 +130,7 @@
       Success  :    out Boolean)
    with Pre => True
    is
-      Raw_EDID : EDID.Raw_EDID_Data := (others => 16#00#);
+      Raw_EDID : EDID.Raw_EDID_Data with Relaxed_Initialization;
    begin
       Success := Config.Valid_Port (Port);
 
diff --git a/common/hw-gfx-gma-display_probing.ads b/common/hw-gfx-gma-display_probing.ads
index 9c59652..ea13329 100644
--- a/common/hw-gfx-gma-display_probing.ads
+++ b/common/hw-gfx-gma-display_probing.ads
@@ -30,7 +30,8 @@
       Port     : in     Active_Port_Type;
       Success  :    out Boolean)
    with
-      Post => (if Success then EDID.Valid (Raw_EDID));
+      Relaxed_Initialization => Raw_EDID,
+      Post => (if Success then Raw_EDID'Initialized and EDID.Valid (Raw_EDID));
 
    procedure Scan_Ports
      (Configs     :    out Pipe_Configs;
diff --git a/common/hw-gfx-gma.adb b/common/hw-gfx-gma.adb
index 39a6426..e26e751 100644
--- a/common/hw-gfx-gma.adb
+++ b/common/hw-gfx-gma.adb
@@ -155,6 +155,10 @@
         (Port_Cfg, Pipe, Pipe_Cfg.Port, Pipe_Cfg.Mode, Success);
 
       if Success then
+         Power_And_Clocks.Power_Up (Pipe_Cfg.Port, Success);
+      end if;
+
+      if Success then
          Connector_Info.Preferred_Link_Setting (Port_Cfg, Success);
       end if;
 
diff --git a/common/i945/hw-gfx-gma-power_and_clocks.adb b/common/i945/hw-gfx-gma-power_and_clocks.adb
index e18d1e3..23d5476 100644
--- a/common/i945/hw-gfx-gma-power_and_clocks.adb
+++ b/common/i945/hw-gfx-gma-power_and_clocks.adb
@@ -128,4 +128,9 @@
       CDClk_Switch := False;
    end Limit_Dotclocks;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      Success := True;
+   end Power_Up;
+
 end HW.GFX.GMA.Power_And_Clocks;
diff --git a/common/i945/hw-gfx-gma-power_and_clocks.ads b/common/i945/hw-gfx-gma-power_and_clocks.ads
index cad2898..10e9d53 100644
--- a/common/i945/hw-gfx-gma-power_and_clocks.ads
+++ b/common/i945/hw-gfx-gma-power_and_clocks.ads
@@ -34,6 +34,10 @@
 
    procedure Power_Set_To (Configs : Pipe_Configs) is null;
 
+   pragma Warnings (GNATprove, Off, "unused variable ""Port""",
+                    Reason => "Needed for a common interface");
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
+   pragma Warnings (GNATprove, On, "unused variable ""Port""");
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is null;
 
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs)
diff --git a/common/ironlake/hw-gfx-gma-power_and_clocks.adb b/common/ironlake/hw-gfx-gma-power_and_clocks.adb
index 6bd43e1..b95f7ff 100644
--- a/common/ironlake/hw-gfx-gma-power_and_clocks.adb
+++ b/common/ironlake/hw-gfx-gma-power_and_clocks.adb
@@ -65,4 +65,9 @@
       CDClk_Switch := False;
    end Limit_Dotclocks;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      Success := True;
+   end Power_Up;
+
 end HW.GFX.GMA.Power_And_Clocks;
diff --git a/common/ironlake/hw-gfx-gma-power_and_clocks.ads b/common/ironlake/hw-gfx-gma-power_and_clocks.ads
index 313239b..eee99d0 100644
--- a/common/ironlake/hw-gfx-gma-power_and_clocks.ads
+++ b/common/ironlake/hw-gfx-gma-power_and_clocks.ads
@@ -34,6 +34,10 @@
 
    procedure Power_Set_To (Configs : Pipe_Configs) is null;
 
+   pragma Warnings (GNATprove, Off, "unused variable ""Port""",
+                    Reason => "Needed for a common interface");
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
+   pragma Warnings (GNATprove, On, "unused variable ""Port""");
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is null;
 
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs)
diff --git a/common/skylake/hw-gfx-gma-power_and_clocks.adb b/common/skylake/hw-gfx-gma-power_and_clocks.adb
index 2841208..acc4753 100644
--- a/common/skylake/hw-gfx-gma-power_and_clocks.adb
+++ b/common/skylake/hw-gfx-gma-power_and_clocks.adb
@@ -409,6 +409,18 @@
       end loop;
    end Power_Set_To;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      case Port is
+         when eDP          => PD_On (DDI_AE);
+         when DP1 | HDMI1  => PD_On (PW2); PD_On (DDI_B);
+         when DP2 | HDMI2  => PD_On (PW2); PD_On (DDI_C);
+         when DP3 | HDMI3  => PD_On (PW2); PD_On (DDI_D);
+         when others       => null;
+      end case;
+      Success := True;
+   end Power_Up;
+
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is
    begin
       for PD in Dynamic_Domain loop
diff --git a/common/skylake/hw-gfx-gma-power_and_clocks.ads b/common/skylake/hw-gfx-gma-power_and_clocks.ads
index e4f2611..f7c5abe 100644
--- a/common/skylake/hw-gfx-gma-power_and_clocks.ads
+++ b/common/skylake/hw-gfx-gma-power_and_clocks.ads
@@ -32,6 +32,7 @@
    procedure Enable_CDClk is null;
 
    procedure Power_Set_To (Configs : Pipe_Configs);
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs);
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs);
 
diff --git a/common/tigerlake/hw-gfx-gma-power_and_clocks.adb b/common/tigerlake/hw-gfx-gma-power_and_clocks.adb
index 0a78217..d9d27bb 100644
--- a/common/tigerlake/hw-gfx-gma-power_and_clocks.adb
+++ b/common/tigerlake/hw-gfx-gma-power_and_clocks.adb
@@ -52,6 +52,11 @@
       pragma Debug (Debug.Put_Line (GNAT.Source_Info.Enclosing_Entity));
    end Power_Set_To;
 
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean) is
+   begin
+      Success := False;
+   end Power_Up;
+
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs) is
    begin
       pragma Debug (Debug.Put_Line (GNAT.Source_Info.Enclosing_Entity));
diff --git a/common/tigerlake/hw-gfx-gma-power_and_clocks.ads b/common/tigerlake/hw-gfx-gma-power_and_clocks.ads
index 72854e8..040d5c1 100644
--- a/common/tigerlake/hw-gfx-gma-power_and_clocks.ads
+++ b/common/tigerlake/hw-gfx-gma-power_and_clocks.ads
@@ -37,6 +37,7 @@
    procedure Enable_CDClk is null;
 
    procedure Power_Set_To (Configs : Pipe_Configs);
+   procedure Power_Up (Port : Active_Port_Type; Success : out Boolean);
    procedure Power_Up (Old_Configs, New_Configs : Pipe_Configs);
    procedure Power_Down (Old_Configs, Tmp_Configs, New_Configs : Pipe_Configs);
    pragma Warnings (On, "subprogram ""*"" has no effect");