xref: /haiku/src/add-ons/kernel/generic/scsi_periph/scsi_periph_int.h (revision 2710b4f5d4251c5cf88c82b0114ea99b0ef46d22)
1 /*
2  * Copyright 2004-2013, Haiku, Inc. All Rights Reserved.
3  * Copyright 2002, Thomas Kurschel. All rights reserved.
4  * Distributed under the terms of the MIT License.
5  */
6 #ifndef __SCSI_PERIPH_INT_H__
7 #define __SCSI_PERIPH_INT_H__
8 
9 
10 #include <stddef.h>
11 
12 #include <scsi_periph.h>
13 #include <device_manager.h>
14 
15 #include "IORequest.h"
16 #include "wrapper.h"
17 
18 
19 enum trim_command {
20 	TRIM_NONE,			// TRIM operation is disabled for this device
21 	TRIM_UNMAP,			// UNMAP command wil be used
22 	TRIM_WRITESAME10,	// WRITE SAME (10) with UNMAP bit enabled will be used
23 	TRIM_WRITESAME16	// WRITE SAME (16) with UNMAP bit enabled will be used
24 };
25 
26 
27 typedef struct scsi_periph_device_info {
28 	struct scsi_periph_handle_info *handles;
29 
30 	::scsi_device scsi_device;
31 	scsi_device_interface *scsi;
32 	periph_device_cookie periph_device;
33 	device_node *node;
34 
35 	bool removal_requested;
36 
37 	bool removable;			// true, if device is removable
38 
39 	enum trim_command unmap_command;	// command to be used to discard free blocks
40 	uint32 max_unmap_lba_count;			// max. number of LBAs in one command
41 	uint32 max_unmap_descriptor_count;	// max. number of ranges in one command
42 
43 	uint32 block_size;
44 	uint32 physical_block_size;
45 	int32 preferred_ccb_size;
46 	int32 rw10_enabled;		// 10 byte r/w commands supported; access must be atomic
47 	int32 next_tag_action;	// queuing flag for next r/w command; access must be atomic
48 
49 	struct mutex mutex;
50 	int std_timeout;
51 
52 	scsi_periph_callbacks *callbacks;
53 } scsi_periph_device_info;
54 
55 typedef struct scsi_periph_handle_info {
56 	scsi_periph_device_info *device;
57 	struct scsi_periph_handle_info *next, *prev;
58 
59 	int pending_error;		// error to be reported on all accesses
60 							// (used to block access after medium change until
61 							//  B_GET_MEDIA_STATUS is called)
62 	periph_handle_cookie periph_handle;
63 } scsi_periph_handle_info;
64 
65 extern device_manager_info *gDeviceManager;
66 
67 
68 // removable.c
69 
70 void periph_media_changed(scsi_periph_device_info *device, scsi_ccb *ccb);
71 void periph_media_changed_public(scsi_periph_device_info *device);
72 status_t periph_get_media_status(scsi_periph_handle_info *handle);
73 err_res periph_send_start_stop(scsi_periph_device_info *device, scsi_ccb *request,
74 	bool start, bool with_LoEj);
75 
76 
77 // error_handling.c
78 
79 err_res periph_check_error(scsi_periph_device_info *device, scsi_ccb *request);
80 
81 
82 // handle.c
83 
84 status_t periph_handle_open(scsi_periph_device_info *device, periph_handle_cookie periph_handle,
85 	scsi_periph_handle_info **res_handle);
86 status_t periph_handle_close(scsi_periph_handle_info *handle);
87 status_t periph_handle_free(scsi_periph_handle_info *handle);
88 
89 
90 // block.c
91 
92 status_t periph_check_capacity(scsi_periph_device_info *device, scsi_ccb *ccb);
93 status_t periph_trim_device(scsi_periph_device_info *device, scsi_ccb *request,
94 	scsi_block_range* ranges, uint32 rangeCount, uint64* trimmedBlocks);
95 
96 
97 // device.c
98 
99 status_t periph_register_device(periph_device_cookie periph_device,
100 	scsi_periph_callbacks *callbacks, scsi_device scsi_device,
101 	scsi_device_interface *scsi, device_node *node, bool removable,
102 	int preferredCcbSize, scsi_periph_device *driver);
103 status_t periph_unregister_device(scsi_periph_device_info *driver);
104 char *periph_compose_device_name(device_node *device_node, const char *prefix);
105 
106 
107 // io.c
108 
109 status_t periph_read_write(scsi_periph_device_info *device, scsi_ccb *request,
110 	uint64 offset, size_t numBlocks, physical_entry* vecs, size_t vecCount,
111 	bool isWrite, size_t* _bytesTransferred);
112 status_t periph_io(scsi_periph_device_info* device, io_operation* operation,
113 	size_t *_bytesTransferred);
114 status_t periph_ioctl(scsi_periph_handle_info *handle, int op,
115 	void *buf, size_t len);
116 void periph_sync_queue_daemon(void *arg, int iteration);
117 status_t vpd_page_get(scsi_periph_device_info *device, scsi_ccb* request,
118 	uint8 page, void* data, uint16 length);
119 
120 
121 // scsi_periph.c
122 
123 status_t periph_safe_exec(scsi_periph_device_info *device, scsi_ccb *request);
124 status_t periph_simple_exec(scsi_periph_device_info *device, void *cdb,
125 	uchar cdb_len, void *data, size_t data_len, int ccb_flags);
126 
127 
128 // sync.c
129 
130 err_res periph_synchronize_cache(scsi_periph_device_info *device,
131 	scsi_ccb *request);
132 
133 #endif	/* __SCSI_PERIPH_INT_H__ */
134