19 * the documentation and/or other materials provided with the
20 * distribution.
21 *
22 * - Neither the name of The Storage Networking Industry Association (SNIA)
23 * nor the names of its contributors may be used to endorse or promote
24 * products derived from this software without specific prior written
25 * permission.
26 *
27 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
28 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
30 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
31 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
37 * POSSIBILITY OF SUCH DAMAGE.
38 */
39 #include <stdlib.h>
40 #include "tlm.h"
41 #include "tlm_proto.h"
42 #include <sys/errno.h>
43
44
45 extern tlm_chain_link_t *tlm_un_ref(tlm_chain_link_t *old_top,
46 tlm_chain_link_t *link);
47
48 static tlm_info_t tlm_info;
49
50 /*
51 * Mutex for concurrent access to job_stats
52 */
53 mutex_t jstat_mtx;
54
55
56 /*
57 * get the number of libraries
58 */
186 link = tlm_info.ti_job_stats;
187 if (link == 0) {
188 /*
189 * our tables are empty
190 */
191 (void) mutex_unlock(&jstat_mtx);
192 return (&fake_job_stats);
193 }
194
195 do {
196 tlm_job_stats_t *job_stats;
197 job_stats = (tlm_job_stats_t *)link->tc_data;
198
199 if (strcmp(job_stats->js_job_name, name) == 0) {
200 link->tc_ref_count++;
201 (void) mutex_unlock(&jstat_mtx);
202 return (job_stats);
203 }
204 link = link->tc_next;
205 } while (link != tlm_info.ti_job_stats);
206 NDMP_LOG(LOG_DEBUG,
207 "TAPE BACKUP> Ref for job [%s] was not found", name);
208 (void) mutex_unlock(&jstat_mtx);
209
210 return (&fake_job_stats);
211 }
212
213 /*
214 * remove a link to the INFO chain
215 */
216 void
217 tlm_un_ref_job_stats(char *name)
218 {
219 tlm_chain_link_t *link;
220
221 (void) mutex_lock(&jstat_mtx);
222 link = tlm_info.ti_job_stats;
223 if (link == 0) {
224 NDMP_LOG(LOG_DEBUG, "TAPE BACKUP>"
225 " Internal error for job [%s], could not delete", name);
226 return;
227 }
228 do {
229 tlm_job_stats_t *job_stats;
230 job_stats = (tlm_job_stats_t *)link->tc_data;
231
232 if (strcmp(job_stats->js_job_name, name) == 0) {
233 tlm_info.ti_job_stats =
234 tlm_un_ref(tlm_info.ti_job_stats, link);
235 (void) mutex_unlock(&jstat_mtx);
236 return;
237 }
238 link = link->tc_next;
239 } while (link != tlm_info.ti_job_stats);
240 (void) mutex_unlock(&jstat_mtx);
241 NDMP_LOG(LOG_DEBUG,
242 "TAPE BACKUP> Delete for job [%s] was not found", name);
243 }
244
245 /*
246 * one party does not care about this blob, can we let it go?
247 */
248 tlm_chain_link_t *
249 tlm_un_ref(tlm_chain_link_t *old_top, tlm_chain_link_t *link)
250 {
251 tlm_chain_link_t *chain_link = old_top;
252 tlm_chain_link_t *new_top;
253
254 /*
255 * count down the number of
256 * interested parties for this blob
257 */
258 link->tc_ref_count--;
259 if (link->tc_ref_count > 0) {
260 /*
261 * there is still interest in this blob,
288 if (link->tc_next == link->tc_prev &&
289 link->tc_next == link) {
290 /*
291 * there is only this one link in the chain
292 * delete this and the chain is empty
293 */
294 new_top = 0;
295 } else {
296 new_top = link->tc_next;
297 }
298 next = link->tc_next;
299 prev = link->tc_prev;
300 prev->tc_next = next;
301 next->tc_prev = prev;
302 free(link->tc_data);
303 free(link);
304 return (new_top);
305 }
306 chain_link = chain_link->tc_next;
307 } while (chain_link != old_top);
308 NDMP_LOG(LOG_DEBUG, "TAPE BACKUP> un_ref target not found.");
309 return (old_top);
310 }
311
312 /*
313 * the following section is global, but not really part of the
314 * public interface. Use of this outside of the tlm_*.c files
315 * is for special cases only.
316 */
317
318 /*
319 * add a new tape library data blob to the list of libraries
320 * returns the new tape library data blob just created
321 */
322 int
323 tlm_insert_new_library(scsi_link_t *slink)
324 {
325 tlm_library_t **p_library = &tlm_info.ti_library;
326 tlm_library_t *library = ndmp_malloc(sizeof (tlm_library_t));
327
328 while (*p_library != NULL) {
|
19 * the documentation and/or other materials provided with the
20 * distribution.
21 *
22 * - Neither the name of The Storage Networking Industry Association (SNIA)
23 * nor the names of its contributors may be used to endorse or promote
24 * products derived from this software without specific prior written
25 * permission.
26 *
27 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
28 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
30 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
31 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
37 * POSSIBILITY OF SUCH DAMAGE.
38 */
39 #include <syslog.h>
40 #include <stdlib.h>
41 #include "tlm.h"
42 #include "tlm_proto.h"
43 #include <sys/errno.h>
44
45
46 extern tlm_chain_link_t *tlm_un_ref(tlm_chain_link_t *old_top,
47 tlm_chain_link_t *link);
48
49 static tlm_info_t tlm_info;
50
51 /*
52 * Mutex for concurrent access to job_stats
53 */
54 mutex_t jstat_mtx;
55
56
57 /*
58 * get the number of libraries
59 */
187 link = tlm_info.ti_job_stats;
188 if (link == 0) {
189 /*
190 * our tables are empty
191 */
192 (void) mutex_unlock(&jstat_mtx);
193 return (&fake_job_stats);
194 }
195
196 do {
197 tlm_job_stats_t *job_stats;
198 job_stats = (tlm_job_stats_t *)link->tc_data;
199
200 if (strcmp(job_stats->js_job_name, name) == 0) {
201 link->tc_ref_count++;
202 (void) mutex_unlock(&jstat_mtx);
203 return (job_stats);
204 }
205 link = link->tc_next;
206 } while (link != tlm_info.ti_job_stats);
207 syslog(LOG_DEBUG,
208 "TAPE BACKUP> Ref for job [%s] was not found", name);
209 (void) mutex_unlock(&jstat_mtx);
210
211 return (&fake_job_stats);
212 }
213
214 /*
215 * remove a link to the INFO chain
216 */
217 void
218 tlm_un_ref_job_stats(char *name)
219 {
220 tlm_chain_link_t *link;
221
222 (void) mutex_lock(&jstat_mtx);
223 link = tlm_info.ti_job_stats;
224 if (link == 0) {
225 syslog(LOG_DEBUG, "TAPE BACKUP>"
226 " Internal error for job [%s], could not delete", name);
227 return;
228 }
229 do {
230 tlm_job_stats_t *job_stats;
231 job_stats = (tlm_job_stats_t *)link->tc_data;
232
233 if (strcmp(job_stats->js_job_name, name) == 0) {
234 tlm_info.ti_job_stats =
235 tlm_un_ref(tlm_info.ti_job_stats, link);
236 (void) mutex_unlock(&jstat_mtx);
237 return;
238 }
239 link = link->tc_next;
240 } while (link != tlm_info.ti_job_stats);
241 (void) mutex_unlock(&jstat_mtx);
242 syslog(LOG_DEBUG,
243 "TAPE BACKUP> Delete for job [%s] was not found", name);
244 }
245
246 /*
247 * one party does not care about this blob, can we let it go?
248 */
249 tlm_chain_link_t *
250 tlm_un_ref(tlm_chain_link_t *old_top, tlm_chain_link_t *link)
251 {
252 tlm_chain_link_t *chain_link = old_top;
253 tlm_chain_link_t *new_top;
254
255 /*
256 * count down the number of
257 * interested parties for this blob
258 */
259 link->tc_ref_count--;
260 if (link->tc_ref_count > 0) {
261 /*
262 * there is still interest in this blob,
289 if (link->tc_next == link->tc_prev &&
290 link->tc_next == link) {
291 /*
292 * there is only this one link in the chain
293 * delete this and the chain is empty
294 */
295 new_top = 0;
296 } else {
297 new_top = link->tc_next;
298 }
299 next = link->tc_next;
300 prev = link->tc_prev;
301 prev->tc_next = next;
302 next->tc_prev = prev;
303 free(link->tc_data);
304 free(link);
305 return (new_top);
306 }
307 chain_link = chain_link->tc_next;
308 } while (chain_link != old_top);
309 syslog(LOG_DEBUG, "TAPE BACKUP> un_ref target not found.");
310 return (old_top);
311 }
312
313 /*
314 * the following section is global, but not really part of the
315 * public interface. Use of this outside of the tlm_*.c files
316 * is for special cases only.
317 */
318
319 /*
320 * add a new tape library data blob to the list of libraries
321 * returns the new tape library data blob just created
322 */
323 int
324 tlm_insert_new_library(scsi_link_t *slink)
325 {
326 tlm_library_t **p_library = &tlm_info.ti_library;
327 tlm_library_t *library = ndmp_malloc(sizeof (tlm_library_t));
328
329 while (*p_library != NULL) {
|