1 /*
2  * Python file objects IO pool functions
3  *
4  * Copyright (C) 2014-2021, Joachim Metz <joachim.metz@gmail.com>
5  *
6  * Refer to AUTHORS for acknowledgements.
7  *
8  * This program is free software: you can redistribute it and/or modify
9  * it under the terms of the GNU Lesser General Public License as published by
10  * the Free Software Foundation, either version 3 of the License, or
11  * (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public License
19  * along with this program.  If not, see <https://www.gnu.org/licenses/>.
20  */
21 
22 #include <common.h>
23 #include <types.h>
24 
25 #include "pyvslvm_file_object_io_handle.h"
26 #include "pyvslvm_file_objects_io_pool.h"
27 #include "pyvslvm_integer.h"
28 #include "pyvslvm_libbfio.h"
29 #include "pyvslvm_libcerror.h"
30 #include "pyvslvm_python.h"
31 
32 /* Initializes the file objects IO pool
33  * Returns 1 if successful or -1 on error
34  */
pyvslvm_file_objects_pool_initialize(libbfio_pool_t ** pool,PyObject * sequence_object,int access_flags,libcerror_error_t ** error)35 int pyvslvm_file_objects_pool_initialize(
36      libbfio_pool_t **pool,
37      PyObject *sequence_object,
38      int access_flags,
39      libcerror_error_t **error )
40 {
41 	libbfio_handle_t *file_io_handle = NULL;
42 	PyObject *file_object            = NULL;
43 	static char *function            = "pyvslvm_file_objects_pool_initialize";
44 	Py_ssize_t sequence_size         = 0;
45 	int element_index                = 0;
46 	int file_io_pool_entry           = 0;
47 	int number_of_elements           = 0;
48 
49 	if( pool == NULL )
50 	{
51 		libcerror_error_set(
52 		 error,
53 		 LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
54 		 LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
55 		 "%s: invalid pool.",
56 		 function );
57 
58 		return( -1 );
59 	}
60 	if( *pool != NULL )
61 	{
62 		libcerror_error_set(
63 		 error,
64 		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
65 		 LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
66 		 "%s: invalid pool value already set.",
67 		 function );
68 
69 		return( -1 );
70 	}
71 	sequence_size = PySequence_Size(
72 	                 sequence_object );
73 
74 	if( sequence_size > (Py_ssize_t) INT_MAX )
75 	{
76 		libcerror_error_set(
77 		 error,
78 		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
79 		 LIBCERROR_RUNTIME_ERROR_VALUE_ALREADY_SET,
80 		 "%s: invalid sequence size value exceeds maximum.",
81 		 function );
82 
83 		goto on_error;
84 	}
85 	number_of_elements = (int) sequence_size;
86 
87 	if( libbfio_pool_initialize(
88 	     pool,
89 	     0,
90 	     LIBBFIO_POOL_UNLIMITED_NUMBER_OF_OPEN_HANDLES,
91 	     error ) != 1 )
92 	{
93 		libcerror_error_set(
94 		 error,
95 		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
96 		 LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
97 		 "%s: unable to create pool.",
98 		 function );
99 
100 		goto on_error;
101 	}
102 	for( element_index = 0;
103 	     element_index < number_of_elements;
104 	     element_index++ )
105 	{
106 		file_object = PySequence_GetItem(
107 		               sequence_object,
108 		               element_index );
109 
110 		if( file_object == NULL )
111 		{
112 			libcerror_error_set(
113 			 error,
114 			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
115 			 LIBCERROR_RUNTIME_ERROR_VALUE_MISSING,
116 			 "%s: missing file object IO handle.",
117 			 function );
118 
119 			goto on_error;
120 		}
121 		if( pyvslvm_file_object_initialize(
122 		     &file_io_handle,
123 		     file_object,
124 		     error ) != 1 )
125 		{
126 			libcerror_error_set(
127 			 error,
128 			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
129 			 LIBCERROR_RUNTIME_ERROR_INITIALIZE_FAILED,
130 			 "%s: unable to create file IO handle.",
131 			 function );
132 
133 			goto on_error;
134 		}
135 		/* Remove the reference created by PySequence_GetItem
136 		 */
137 		Py_DecRef(
138 		 (PyObject *) file_object );
139 
140 		file_object = NULL;
141 
142 		if( libbfio_pool_append_handle(
143 		     *pool,
144 		     &file_io_pool_entry,
145 		     file_io_handle,
146 		     access_flags,
147 		     error ) != 1 )
148 		{
149 			libcerror_error_set(
150 			 error,
151 			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
152 			 LIBCERROR_RUNTIME_ERROR_APPEND_FAILED,
153 			 "%s: unable to append file IO handle to pool.",
154 			 function );
155 
156 			goto on_error;
157 		}
158 		file_io_handle = NULL;
159 	}
160 	return( 1 );
161 
162 on_error:
163 	if( file_object != NULL )
164 	{
165 		Py_DecRef(
166 		 (PyObject *) file_object );
167 	}
168 	if( file_io_handle != NULL )
169 	{
170 		libbfio_handle_free(
171 		 &file_io_handle,
172 		 NULL );
173 	}
174 	if( *pool != NULL )
175 	{
176 		libbfio_pool_free(
177 		 pool,
178 		 NULL );
179 	}
180 	return( -1 );
181 }
182 
183