int zuluCryptUnmountVolume( const char * device,char ** m_point )
{
	int h = 3 ;

	char * e ;

	size_t s ;

	stringList_t stl ;

	StringListIterator it ;
	StringListIterator end ;

	ssize_t r ;

	string_t st ;
	string_t xt ;

	if( StringPrefixEqual( device,"/dev/loop" ) ){

		/*
		 * zuluCryptLoopDeviceAddress() is defined in create_loop_device.c
		 */

		e = zuluCryptLoopDeviceAddress( device ) ;

		if( e == NULL ){

			return h ;
		}else{
			stl = _get_mount_entries( e ) ;
			StringFree( e ) ;
		}
	}else{
		stl = _get_mount_entries( device ) ;
	}

	s = StringListSize( stl ) ;

	if( s == 0 ){

		/*
		 * volume appear to not be mounted.
		 */

	}else if( s == 1 ){

		/*
		 * there is only one mount point for the volume,unmount it normally
		 */

		h = _zuluCryptUnmountVolume_0( StringListStringAtFirstPlace( stl ),m_point ) ;
	}else{
		/*
		 * There are multiple mount points for the same volume.
		 *
		 * Try to figure out which one among the mount points is ours and then try
		 * first to unmount the rest of them.
		 */

		r = StringListHasSequence( stl," /run/media/private/" ) ;

		if( r == -1 ){

			/*
			 * Probable reason for getting here is if a user use a home mount point path,
			 * we dont know the path because we dont know the user we are serving
			 * and hence we bail out with an error.
			 */
			h = 10 ;
		}else{
			/*
			 * We got our mount point,take it out of the list to use it last
			 */
			st = StringListDetachAt( stl,r ) ;

			StringListGetIterators( stl,&it,&end ) ;

			while( it != end ){

				xt = *it ;

				it++ ;

				if( _zuluCryptUnmountVolume_0( xt,NULL ) != 0 ){

					/*
					 * Failed to unmount one of the extra mount points,
					 * bail out with an error.
					 */
					h = 10 ;

					break ;
				}
			}

			if( h != 10 ){

				/*
				 * Attempt to unmount our mount point last.
				 */
				h = _zuluCryptUnmountVolume_0( st,m_point ) ;
			}

			StringDelete( &st ) ;
		}
	}

	if( h != 0 && h != 3 && h != 4 && h != 1 && h != 10 ){

		h = 2 ;
	}

	StringListDelete( &stl ) ;

	return h ;
}
Exemple #2
0
int zuluCryptBindMountVolume( const char * device,string_t z_path,unsigned long flags )
{
	struct stat st ;
	string_t path ;
	string_t tmp ;
	ssize_t index = StringLastIndexOfChar( z_path,'/' ) ;
	const char * o_path = StringContent( z_path ) ;
	const char * m_path ;
	const char * e ;
	int xt ;

	stringList_t stl ;

	mode_t mode = S_IRWXU | S_IRGRP | S_IXGRP | S_IXOTH | S_IROTH ;

	if( index == -1 ){
		return 1 ;
	}
	if( device ){;}

	zuluCryptSecurityGainElevatedPrivileges() ;
	/*
	 * zuluCryptGetMoutedListFromMountInfo() is defined in ../lib/process_mountinfo.c
	 */
	stl = zuluCryptGetMoutedListFromMountInfo() ;

	path = String( "/run/media/public/" ) ;
	m_path = StringAppend( path,o_path + index + 1 ) ;

	#define path_does_not_exist( x ) stat( x,&st ) != 0
	#define path_does_exist( x ) stat( x,&st ) == 0

	if( path_does_not_exist( "/run" ) ){
		mkdir( "/run",mode ) ;
		_chown( "/run",0,0 ) ;
	}
	if( path_does_not_exist( "/run/media" ) ){
		mkdir( "/run/media",mode ) ;
		_chown( "/run/media",0,0 ) ;
	}
	if( path_does_not_exist( "/run/media/public" ) ){
		mkdir( "/run/media/public",mode ) ;
		_chown( "/run/media/public",0,0 ) ;
	}
	if( path_does_exist( m_path ) ){
		/*
		 * bind mount point exists,this will happen if the mount point is already taken or a mount point folder
		 * was not autodeleted for some reason
		 */
		tmp = StringCopy( path ) ;
		e = StringAppend( tmp," " ) ;

		if( StringListHasSequence( stl,e ) != -1 ){
			/*
			 * An attempt is made to bind mount on a path already bind mounted path,dont attempt to mount
			 */
			xt = 1 ;
		}else{
			/*
			 * the mount point folder is there for some reason but is not being used.
			 */
			xt = mount( o_path,m_path,"",flags|MS_BIND,"" ) ;
		}
		StringDelete( &tmp ) ;
	}else{
		mkdir( m_path,S_IRWXU | S_IRWXG | S_IRWXG ) ;
		_chown( m_path,0,0 ) ;
		xt = mount( o_path,m_path,"",flags|MS_BIND,"" ) ;
		if( xt != 0 ){
			rmdir( m_path ) ;
		}
	}

	StringListDelete( &stl ) ;
	StringDelete( &path ) ;
	zuluCryptSecurityDropElevatedPrivileges() ;
	return xt ;
}