@@ -306,119 +306,49 @@ func printSystemInfo() {
306306 fmt .Printf (" - Filesystem isolation: true\n " )
307307}
308308
309+ // Update the run function to use the new Pull logic
309310func run () {
310- // Adjust the path to include the mock image directory during testing
311- if os . Getenv ( "TEST_ENV" ) == "true" {
312- os .Setenv ( "PATH" , os . Getenv ( "PATH" ) + ":" + imagesDir )
311+ if len ( os . Args ) < 3 {
312+ fmt . Println ( "Error: Image name required for run" )
313+ os .Exit ( 1 )
313314 }
314315
315- // Generate a container ID
316- containerID := fmt .Sprintf ("container-%d" , time .Now ().Unix ())
317- fmt .Printf ("Starting container %s\n " , containerID )
318-
319- // Check if the image exists before proceeding
320316 imageName := os .Args [2 ]
321- imagePath := filepath .Join (imagesDir , imageName )
322- if _ , err := os .Stat (imagePath ); os .IsNotExist (err ) {
323- fmt .Printf ("Image '%s' not found. Fetching the image...\n " , imageName )
324- if err := fetchImage (imageName ); err != nil {
325- fmt .Printf ("Error: Failed to fetch image '%s': %v\n " , imageName , err )
326- os .Exit (1 )
327- }
328- fmt .Printf ("Image '%s' fetched successfully.\n " , imageName )
317+ registry := NewDockerHubRegistry ()
318+
319+ fmt .Printf ("Fetching image '%s'...\n " , imageName )
320+ image , err := Pull (registry , imageName )
321+ if err != nil {
322+ fmt .Printf ("Error: Failed to fetch image '%s': %v\n " , imageName , err )
323+ os .Exit (1 )
329324 }
325+ fmt .Printf ("Image '%s' fetched successfully.\n " , imageName )
330326
331327 // Create rootfs for this container
328+ containerID := fmt .Sprintf ("container-%d" , time .Now ().Unix ())
332329 rootfs := filepath .Join (baseDir , "containers" , containerID , "rootfs" )
333330
334- // Instead of calling createMinimalRootfs directly:
335- // 1. Create a base layer if it doesn't exist
336- baseLayerID := "base-layer"
337- baseLayerPath := filepath .Join (baseDir , "layers" , baseLayerID )
338-
339- if _ , err := os .Stat (baseLayerPath ); os .IsNotExist (err ) {
340- // Create the base layer
341- if err := os .MkdirAll (baseLayerPath , 0755 ); err != nil {
342- fmt .Printf ("Error creating base layer directory: %v\n " , err )
343- os .Exit (1 )
344- }
345-
346- // Initialize the base layer with minimal rootfs content
347- must (initializeBaseLayer (baseLayerPath ))
348-
349- // Save layer metadata
350- layer := ImageLayer {
351- ID : baseLayerID ,
352- Created : time .Now (),
353- BaseLayerPath : baseLayerPath ,
354- }
355-
356- if err := saveLayerMetadata (layer ); err != nil {
357- fmt .Printf ("Warning: Failed to save layer metadata: %v\n " , err )
358- }
359- }
360-
361- // Fix permission issue by ensuring correct ownership and permissions for the base layer
362- if err := os .Chmod (baseLayerPath , 0755 ); err != nil {
363- fmt .Printf ("Error setting permissions for base layer: %v\n " , err )
331+ if err := os .MkdirAll (rootfs , 0755 ); err != nil {
332+ fmt .Printf ("Error: Failed to create rootfs for container '%s': %v\n " , containerID , err )
364333 os .Exit (1 )
365334 }
366335
367- // 2. Create an app layer for this specific container (optional)
368- appLayerID := "app-layer-" + containerID
369- appLayerPath := filepath .Join (baseDir , "layers" , appLayerID )
370-
371- // Use the appLayerID variable to log its creation
372- fmt .Printf ("App layer created with ID: %s\n " , appLayerID )
373-
374- // You could add container-specific files to the app layer here
375- // For now, we'll just use the base layer
376-
377- // Save layer metadata including app layer path
378- layer := ImageLayer {
379- ID : appLayerID ,
380- Created : time .Now (),
381- BaseLayerPath : baseLayerPath ,
382- AppLayerPath : appLayerPath ,
383- }
384-
385- if err := saveLayerMetadata (layer ); err != nil {
386- fmt .Printf ("Warning: Failed to save layer metadata: %v\n " , err )
387- }
388-
389- // 3. Mount the layers to create the container rootfs
390- layers := []string {baseLayerID } // Add appLayerID if you created one
391- must (mountLayeredFilesystem (layers , rootfs ))
392-
393- // Write the PID of the current process to a file
394- pidFile := filepath .Join (baseDir , "containers" , containerID , "pid" )
395- fmt .Printf ("Debug: Writing PID file for container %s at %s\n " , containerID , pidFile )
396- fmt .Printf ("Debug: Current process PID is %d\n " , os .Getpid ())
397- if err := os .WriteFile (pidFile , []byte (fmt .Sprintf ("%d" , os .Getpid ())), 0644 ); err != nil {
398- fmt .Printf ("Error: Failed to write PID file for container %s: %v\n " , containerID , err )
336+ if err := copyDir (image .RootFS , rootfs ); err != nil {
337+ fmt .Printf ("Error: Failed to copy rootfs for container '%s': %v\n " , containerID , err )
399338 os .Exit (1 )
400339 }
401340
402- // Fix deadlock by adding a timeout mechanism
403- if len (os .Args ) < 4 {
404- fmt .Println ("No command provided. Keeping the container process alive with a timeout." )
405- timeout := time .After (10 * time .Minute ) // Set a timeout of 10 minutes
406- select {
407- case <- timeout :
408- fmt .Println ("Timeout reached. Exiting container process." )
409- os .Exit (0 )
410- }
411- }
341+ fmt .Printf ("Starting container %s\n " , containerID )
412342
413- // Update the fallback logic to avoid using unshare entirely in limited isolation
414- if hasNamespacePrivileges && ! inContainer {
415- // Full isolation approach for pure Linux environments
416- runWithNamespaces (containerID , rootfs , os .Args [2 ], os .Args [3 :])
417- } else {
418- runWithoutNamespaces (containerID , rootfs , os .Args [2 ], os .Args [3 :])
343+ // Execute the command in the container
344+ if len (os .Args ) < 4 {
345+ fmt .Println ("Error: Command required for run" )
346+ os .Exit (1 )
419347 }
420348
421- fmt .Printf ("Container %s exited\n " , containerID )
349+ command := os .Args [3 ]
350+ args := os .Args [4 :]
351+ runWithoutNamespaces (containerID , rootfs , command , args )
422352}
423353
424354func initializeBaseLayer (baseLayerPath string ) error {
0 commit comments