@@ -1433,6 +1433,12 @@ func (b *Builder) setupMounts(mountPoint string, spec *specs.Spec, bundlePath st
14331433 mounts = append (mounts , mount )
14341434 }
14351435
1436+ // Some mounts require env vars to be set, do these here
1437+ spec .Process .Env = append (spec .Process .Env , mountArtifacts .SecretEnvVars ... )
1438+ if mountArtifacts .SSHAuthSock != "" {
1439+ spec .Process .Env = append (spec .Process .Env , "SSH_AUTH_SOCK=" + mountArtifacts .SSHAuthSock )
1440+ }
1441+
14361442 // Set the list in the spec.
14371443 spec .Mounts = mounts
14381444 succeeded = true
@@ -1522,6 +1528,7 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
15221528 intermediateMounts := make ([]string , 0 , len (mounts ))
15231529 finalMounts := make ([]specs.Mount , 0 , len (mounts ))
15241530 agents := make ([]* sshagent.AgentServer , 0 , len (mounts ))
1531+ var secretEnvVars []string
15251532 defaultSSHSock := ""
15261533 targetLocks := []* lockfile.LockFile {}
15271534 var overlayDirs []string
@@ -1561,11 +1568,7 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
15611568 }
15621569 }()
15631570 for _ , mount := range mounts {
1564- var mountSpec * specs.Mount
1565- var err error
1566- var envFile , image , bundleMountsDir , overlayDir , intermediateMount string
1567- var agent * sshagent.AgentServer
1568- var tl * lockfile.LockFile
1571+ var bundleMountsDir string
15691572
15701573 tokens := strings .Split (mount , "," )
15711574
@@ -1583,18 +1586,21 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
15831586 }
15841587 switch mountType {
15851588 case "secret" :
1586- mountSpec , envFile , err = b .getSecretMount (tokens , sources .Secrets , idMaps , sources .WorkDir )
1589+ mountOrEnvSpec , err : = b .getSecretMount (tokens , sources .Secrets , idMaps , sources .WorkDir )
15871590 if err != nil {
15881591 return nil , nil , err
15891592 }
1590- if mountSpec != nil {
1591- finalMounts = append (finalMounts , * mountSpec )
1592- if envFile != "" {
1593- tmpFiles = append (tmpFiles , envFile )
1594- }
1593+ if mountOrEnvSpec .Mount != nil {
1594+ finalMounts = append (finalMounts , * mountOrEnvSpec .Mount )
1595+ }
1596+ if mountOrEnvSpec .EnvFile != "" {
1597+ tmpFiles = append (tmpFiles , mountOrEnvSpec .EnvFile )
1598+ }
1599+ if mountOrEnvSpec .EnvVariable != "" {
1600+ secretEnvVars = append (secretEnvVars , mountOrEnvSpec .EnvVariable )
15951601 }
15961602 case "ssh" :
1597- mountSpec , agent , err = b .getSSHMount (tokens , len (agents ), sources .SSHSources , idMaps )
1603+ mountSpec , agent , err : = b .getSSHMount (tokens , len (agents ), sources .SSHSources , idMaps )
15981604 if err != nil {
15991605 return nil , nil , err
16001606 }
@@ -1607,11 +1613,12 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
16071613 }
16081614 case define .TypeBind :
16091615 if bundleMountsDir == "" {
1616+ var err error
16101617 if bundleMountsDir , err = os .MkdirTemp (bundlePath , "mounts" ); err != nil {
16111618 return nil , nil , err
16121619 }
16131620 }
1614- mountSpec , image , intermediateMount , overlayDir , err = b .getBindMount (tokens , sources .SystemContext , sources .ContextDir , sources .StageMountPoints , idMaps , sources .WorkDir , bundleMountsDir )
1621+ mountSpec , image , intermediateMount , overlayDir , err : = b .getBindMount (tokens , sources .SystemContext , sources .ContextDir , sources .StageMountPoints , idMaps , sources .WorkDir , bundleMountsDir )
16151622 if err != nil {
16161623 return nil , nil , err
16171624 }
@@ -1626,18 +1633,19 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
16261633 }
16271634 finalMounts = append (finalMounts , * mountSpec )
16281635 case "tmpfs" :
1629- mountSpec , err = b .getTmpfsMount (tokens , idMaps , sources .WorkDir )
1636+ mountSpec , err : = b .getTmpfsMount (tokens , idMaps , sources .WorkDir )
16301637 if err != nil {
16311638 return nil , nil , err
16321639 }
16331640 finalMounts = append (finalMounts , * mountSpec )
16341641 case "cache" :
16351642 if bundleMountsDir == "" {
1643+ var err error
16361644 if bundleMountsDir , err = os .MkdirTemp (bundlePath , "mounts" ); err != nil {
16371645 return nil , nil , err
16381646 }
16391647 }
1640- mountSpec , image , intermediateMount , overlayDir , tl , err = b .getCacheMount (tokens , sources .SystemContext , sources .StageMountPoints , idMaps , sources .WorkDir , bundleMountsDir )
1648+ mountSpec , image , intermediateMount , overlayDir , tl , err : = b .getCacheMount (tokens , sources .SystemContext , sources .StageMountPoints , idMaps , sources .WorkDir , bundleMountsDir )
16411649 if err != nil {
16421650 return nil , nil , err
16431651 }
@@ -1666,6 +1674,7 @@ func (b *Builder) runSetupRunMounts(bundlePath string, mounts []string, sources
16661674 SSHAuthSock : defaultSSHSock ,
16671675 TargetLocks : targetLocks ,
16681676 IntermediateMounts : intermediateMounts ,
1677+ SecretEnvVars : secretEnvVars ,
16691678 }
16701679 return finalMounts , artifacts , nil
16711680}
@@ -1731,13 +1740,17 @@ func (b *Builder) getTmpfsMount(tokens []string, idMaps IDMaps, workDir string)
17311740 return & volumes [0 ], nil
17321741}
17331742
1734- func (b * Builder ) getSecretMount (tokens []string , secrets map [string ]define.Secret , idMaps IDMaps , workdir string ) (_ * specs.Mount , _ string , retErr error ) {
1735- errInvalidSyntax := errors .New ("secret should have syntax id=id[,target=path,required=bool,mode=uint,uid=uint,gid=uint" )
1743+ func (b * Builder ) getSecretMount (tokens []string , secrets map [string ]define.Secret , idMaps IDMaps , workdir string ) (rv struct {
1744+ Mount * specs.Mount // set if mount created
1745+ EnvFile string // set if caller mount created from temp created env file
1746+ EnvVariable string // set if caller should add to env variable list
1747+ }, retErr error ,
1748+ ) {
1749+ errInvalidSyntax := errors .New ("secret should have syntax id=id[,target=path,required=bool,mode=uint,uid=uint,gid=uint,env=dstVarName" )
17361750 if len (tokens ) == 0 {
1737- return nil , "" , errInvalidSyntax
1751+ return rv , errInvalidSyntax
17381752 }
1739- var err error
1740- var id , target string
1753+ var id , target , env string
17411754 var required bool
17421755 var uid , gid uint32
17431756 var mode uint32 = 0o400
@@ -1757,110 +1770,123 @@ func (b *Builder) getSecretMount(tokens []string, secrets map[string]define.Secr
17571770 case "required" :
17581771 required = true
17591772 if len (kv ) > 1 {
1773+ var err error
17601774 required , err = strconv .ParseBool (kv [1 ])
17611775 if err != nil {
1762- return nil , "" , errInvalidSyntax
1776+ return rv , errInvalidSyntax
17631777 }
17641778 }
17651779 case "mode" :
17661780 mode64 , err := strconv .ParseUint (kv [1 ], 8 , 32 )
17671781 if err != nil {
1768- return nil , "" , errInvalidSyntax
1782+ return rv , errInvalidSyntax
17691783 }
17701784 mode = uint32 (mode64 )
17711785 case "uid" :
17721786 uid64 , err := strconv .ParseUint (kv [1 ], 10 , 32 )
17731787 if err != nil {
1774- return nil , "" , errInvalidSyntax
1788+ return rv , errInvalidSyntax
17751789 }
17761790 uid = uint32 (uid64 )
17771791 case "gid" :
17781792 gid64 , err := strconv .ParseUint (kv [1 ], 10 , 32 )
17791793 if err != nil {
1780- return nil , "" , errInvalidSyntax
1794+ return rv , errInvalidSyntax
17811795 }
17821796 gid = uint32 (gid64 )
1797+ case "env" :
1798+ if kv [1 ] == "" {
1799+ return rv , errInvalidSyntax
1800+ }
1801+ env = kv [1 ]
17831802 default :
1784- return nil , "" , errInvalidSyntax
1803+ return rv , errInvalidSyntax
17851804 }
17861805 }
17871806
17881807 if id == "" {
1789- return nil , "" , errInvalidSyntax
1790- }
1791- // Default location for secrets is /run/secrets/id
1792- if target == "" {
1793- target = "/run/secrets/" + id
1808+ return rv , errInvalidSyntax
17941809 }
17951810
1811+ // first fetch the secret data
17961812 secr , ok := secrets [id ]
17971813 if ! ok {
17981814 if required {
1799- return nil , "" , fmt .Errorf ("secret required but no secret with id %q found" , id )
1815+ return rv , fmt .Errorf ("secret required but no secret with id %q found" , id )
18001816 }
1801- return nil , "" , nil
1817+ return rv , nil
1818+ }
1819+ data , err := secr .ResolveValue ()
1820+ if err != nil {
1821+ return rv , err
1822+ }
1823+
1824+ // if env is set, then we can return now
1825+ if env != "" {
1826+ rv .EnvVariable = env + "=" + string (data )
1827+ return rv , nil
1828+ }
1829+ // else we fallback to default behaviour of creating mount
1830+
1831+ // Default location for secrets is /run/secrets/id
1832+ if target == "" {
1833+ target = "/run/secrets/" + id
18021834 }
1803- var data []byte
1804- var envFile string
1835+
18051836 var ctrFileOnHost string
18061837
18071838 switch secr .SourceType {
18081839 case "env" :
1809- data = []byte (os .Getenv (secr .Source ))
18101840 tmpFile , err := os .CreateTemp (tmpdir .GetTempDir (), "buildah*" )
18111841 if err != nil {
1812- return nil , "" , err
1842+ return rv , err
18131843 }
18141844 defer func () {
18151845 if retErr != nil {
18161846 os .Remove (tmpFile .Name ())
18171847 }
18181848 }()
1819- envFile = tmpFile .Name ()
1849+ rv . EnvFile = tmpFile .Name ()
18201850 ctrFileOnHost = tmpFile .Name ()
18211851 case "file" :
18221852 containerWorkingDir , err := b .store .ContainerDirectory (b .ContainerID )
18231853 if err != nil {
1824- return nil , "" , err
1825- }
1826- data , err = os .ReadFile (secr .Source )
1827- if err != nil {
1828- return nil , "" , err
1854+ return rv , err
18291855 }
18301856 ctrFileOnHost = filepath .Join (containerWorkingDir , "secrets" , digest .FromString (id ).Encoded ()[:16 ])
18311857 default :
1832- return nil , "" , errors .New ("invalid source secret type" )
1858+ return rv , errors .New ("invalid source secret type" )
18331859 }
18341860
18351861 // Copy secrets to container working dir (or tmp dir if it's an env), since we need to chmod,
18361862 // chown and relabel it for the container user and we don't want to mess with the original file
18371863 if err := os .MkdirAll (filepath .Dir (ctrFileOnHost ), 0o755 ); err != nil {
1838- return nil , "" , err
1864+ return rv , err
18391865 }
18401866 if err := os .WriteFile (ctrFileOnHost , data , 0o644 ); err != nil {
1841- return nil , "" , err
1867+ return rv , err
18421868 }
18431869
18441870 if err := relabel (ctrFileOnHost , b .MountLabel , false ); err != nil {
1845- return nil , "" , err
1871+ return rv , err
18461872 }
18471873 hostUID , hostGID , err := util .GetHostIDs (idMaps .uidmap , idMaps .gidmap , uid , gid )
18481874 if err != nil {
1849- return nil , "" , err
1875+ return rv , err
18501876 }
18511877 if err := os .Lchown (ctrFileOnHost , int (hostUID ), int (hostGID )); err != nil {
1852- return nil , "" , err
1878+ return rv , err
18531879 }
18541880 if err := os .Chmod (ctrFileOnHost , os .FileMode (mode )); err != nil {
1855- return nil , "" , err
1881+ return rv , err
18561882 }
1857- newMount := specs.Mount {
1883+ rv . Mount = & specs.Mount {
18581884 Destination : target ,
18591885 Type : define .TypeBind ,
18601886 Source : ctrFileOnHost ,
18611887 Options : append (define .BindOptions , "rprivate" , "ro" ),
18621888 }
1863- return & newMount , envFile , nil
1889+ return rv , nil
18641890}
18651891
18661892// getSSHMount parses the --mount type=ssh flag in the Containerfile, checks if there's an ssh source provided, and creates and starts an ssh-agent to be forwarded into the container
0 commit comments