Commit cf393950 authored by Alon Mizrahi's avatar Alon Mizrahi Committed by Oded Gabbay

habanalabs: add custom timeout flag per cs

There is a need to allow to user to send command submissions with
custom timeout as some CS take longer than the max timeout that is
used by default.
Signed-off-by: default avatarAlon Mizrahi <amizrahi@habana.ai>
Reviewed-by: default avatarOded Gabbay <ogabbay@kernel.org>
Signed-off-by: default avatarOded Gabbay <ogabbay@kernel.org>
parent cd5def80
...@@ -467,8 +467,7 @@ static void cs_handle_tdr(struct hl_device *hdev, struct hl_cs *cs) ...@@ -467,8 +467,7 @@ static void cs_handle_tdr(struct hl_device *hdev, struct hl_cs *cs)
if (next_entry_found && !next->tdr_active) { if (next_entry_found && !next->tdr_active) {
next->tdr_active = true; next->tdr_active = true;
schedule_delayed_work(&next->work_tdr, schedule_delayed_work(&next->work_tdr, next->timeout_jiffies);
hdev->timeout_jiffies);
} }
spin_unlock(&hdev->cs_mirror_lock); spin_unlock(&hdev->cs_mirror_lock);
...@@ -622,7 +621,7 @@ static void cs_timedout(struct work_struct *work) ...@@ -622,7 +621,7 @@ static void cs_timedout(struct work_struct *work)
static int allocate_cs(struct hl_device *hdev, struct hl_ctx *ctx, static int allocate_cs(struct hl_device *hdev, struct hl_ctx *ctx,
enum hl_cs_type cs_type, u64 user_sequence, enum hl_cs_type cs_type, u64 user_sequence,
struct hl_cs **cs_new) struct hl_cs **cs_new, u32 flags, u32 timeout)
{ {
struct hl_cs_counters_atomic *cntr; struct hl_cs_counters_atomic *cntr;
struct hl_fence *other = NULL; struct hl_fence *other = NULL;
...@@ -649,6 +648,8 @@ static int allocate_cs(struct hl_device *hdev, struct hl_ctx *ctx, ...@@ -649,6 +648,8 @@ static int allocate_cs(struct hl_device *hdev, struct hl_ctx *ctx,
cs->submitted = false; cs->submitted = false;
cs->completed = false; cs->completed = false;
cs->type = cs_type; cs->type = cs_type;
cs->timestamp = !!(flags & HL_CS_FLAGS_TIMESTAMP);
cs->timeout_jiffies = timeout;
INIT_LIST_HEAD(&cs->job_list); INIT_LIST_HEAD(&cs->job_list);
INIT_DELAYED_WORK(&cs->work_tdr, cs_timedout); INIT_DELAYED_WORK(&cs->work_tdr, cs_timedout);
kref_init(&cs->refcount); kref_init(&cs->refcount);
...@@ -1092,7 +1093,8 @@ static int cs_staged_submission(struct hl_device *hdev, struct hl_cs *cs, ...@@ -1092,7 +1093,8 @@ static int cs_staged_submission(struct hl_device *hdev, struct hl_cs *cs,
} }
static int cs_ioctl_default(struct hl_fpriv *hpriv, void __user *chunks, static int cs_ioctl_default(struct hl_fpriv *hpriv, void __user *chunks,
u32 num_chunks, u64 *cs_seq, u32 flags) u32 num_chunks, u64 *cs_seq, u32 flags,
u32 timeout)
{ {
bool staged_mid, int_queues_only = true; bool staged_mid, int_queues_only = true;
struct hl_device *hdev = hpriv->hdev; struct hl_device *hdev = hpriv->hdev;
...@@ -1121,11 +1123,11 @@ static int cs_ioctl_default(struct hl_fpriv *hpriv, void __user *chunks, ...@@ -1121,11 +1123,11 @@ static int cs_ioctl_default(struct hl_fpriv *hpriv, void __user *chunks,
staged_mid = false; staged_mid = false;
rc = allocate_cs(hdev, hpriv->ctx, CS_TYPE_DEFAULT, rc = allocate_cs(hdev, hpriv->ctx, CS_TYPE_DEFAULT,
staged_mid ? user_sequence : ULLONG_MAX, &cs); staged_mid ? user_sequence : ULLONG_MAX, &cs, flags,
timeout);
if (rc) if (rc)
goto free_cs_chunk_array; goto free_cs_chunk_array;
cs->timestamp = !!(flags & HL_CS_FLAGS_TIMESTAMP);
*cs_seq = cs->sequence; *cs_seq = cs->sequence;
hl_debugfs_add_cs(cs); hl_debugfs_add_cs(cs);
...@@ -1323,7 +1325,8 @@ static int hl_submit_pending_cb(struct hl_fpriv *hpriv) ...@@ -1323,7 +1325,8 @@ static int hl_submit_pending_cb(struct hl_fpriv *hpriv)
list_move_tail(&pending_cb->cb_node, &local_cb_list); list_move_tail(&pending_cb->cb_node, &local_cb_list);
spin_unlock(&ctx->pending_cb_lock); spin_unlock(&ctx->pending_cb_lock);
rc = allocate_cs(hdev, ctx, CS_TYPE_DEFAULT, ULLONG_MAX, &cs); rc = allocate_cs(hdev, ctx, CS_TYPE_DEFAULT, ULLONG_MAX, &cs, 0,
hdev->timeout_jiffies);
if (rc) if (rc)
goto add_list_elements; goto add_list_elements;
...@@ -1424,7 +1427,7 @@ static int hl_cs_ctx_switch(struct hl_fpriv *hpriv, union hl_cs_args *args, ...@@ -1424,7 +1427,7 @@ static int hl_cs_ctx_switch(struct hl_fpriv *hpriv, union hl_cs_args *args,
rc = 0; rc = 0;
} else { } else {
rc = cs_ioctl_default(hpriv, chunks, num_chunks, rc = cs_ioctl_default(hpriv, chunks, num_chunks,
cs_seq, 0); cs_seq, 0, hdev->timeout_jiffies);
} }
mutex_unlock(&hpriv->restore_phase_mutex); mutex_unlock(&hpriv->restore_phase_mutex);
...@@ -1594,7 +1597,7 @@ static int cs_ioctl_signal_wait_create_jobs(struct hl_device *hdev, ...@@ -1594,7 +1597,7 @@ static int cs_ioctl_signal_wait_create_jobs(struct hl_device *hdev,
static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type, static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type,
void __user *chunks, u32 num_chunks, void __user *chunks, u32 num_chunks,
u64 *cs_seq, bool timestamp) u64 *cs_seq, u32 flags, u32 timeout)
{ {
struct hl_cs_chunk *cs_chunk_array, *chunk; struct hl_cs_chunk *cs_chunk_array, *chunk;
struct hw_queue_properties *hw_queue_prop; struct hw_queue_properties *hw_queue_prop;
...@@ -1700,7 +1703,7 @@ static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type, ...@@ -1700,7 +1703,7 @@ static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type,
} }
} }
rc = allocate_cs(hdev, ctx, cs_type, ULLONG_MAX, &cs); rc = allocate_cs(hdev, ctx, cs_type, ULLONG_MAX, &cs, flags, timeout);
if (rc) { if (rc) {
if (cs_type == CS_TYPE_WAIT || if (cs_type == CS_TYPE_WAIT ||
cs_type == CS_TYPE_COLLECTIVE_WAIT) cs_type == CS_TYPE_COLLECTIVE_WAIT)
...@@ -1708,8 +1711,6 @@ static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type, ...@@ -1708,8 +1711,6 @@ static int cs_ioctl_signal_wait(struct hl_fpriv *hpriv, enum hl_cs_type cs_type,
goto free_cs_chunk_array; goto free_cs_chunk_array;
} }
cs->timestamp = !!timestamp;
/* /*
* Save the signal CS fence for later initialization right before * Save the signal CS fence for later initialization right before
* hanging the wait CS on the queue. * hanging the wait CS on the queue.
...@@ -1767,7 +1768,7 @@ int hl_cs_ioctl(struct hl_fpriv *hpriv, void *data) ...@@ -1767,7 +1768,7 @@ int hl_cs_ioctl(struct hl_fpriv *hpriv, void *data)
enum hl_cs_type cs_type; enum hl_cs_type cs_type;
u64 cs_seq = ULONG_MAX; u64 cs_seq = ULONG_MAX;
void __user *chunks; void __user *chunks;
u32 num_chunks, flags; u32 num_chunks, flags, timeout;
int rc; int rc;
rc = hl_cs_sanity_checks(hpriv, args); rc = hl_cs_sanity_checks(hpriv, args);
...@@ -1793,16 +1794,20 @@ int hl_cs_ioctl(struct hl_fpriv *hpriv, void *data) ...@@ -1793,16 +1794,20 @@ int hl_cs_ioctl(struct hl_fpriv *hpriv, void *data)
!(flags & HL_CS_FLAGS_STAGED_SUBMISSION_FIRST)) !(flags & HL_CS_FLAGS_STAGED_SUBMISSION_FIRST))
cs_seq = args->in.seq; cs_seq = args->in.seq;
timeout = flags & HL_CS_FLAGS_CUSTOM_TIMEOUT
? msecs_to_jiffies(args->in.timeout * 1000)
: hpriv->hdev->timeout_jiffies;
switch (cs_type) { switch (cs_type) {
case CS_TYPE_SIGNAL: case CS_TYPE_SIGNAL:
case CS_TYPE_WAIT: case CS_TYPE_WAIT:
case CS_TYPE_COLLECTIVE_WAIT: case CS_TYPE_COLLECTIVE_WAIT:
rc = cs_ioctl_signal_wait(hpriv, cs_type, chunks, num_chunks, rc = cs_ioctl_signal_wait(hpriv, cs_type, chunks, num_chunks,
&cs_seq, args->in.cs_flags & HL_CS_FLAGS_TIMESTAMP); &cs_seq, args->in.cs_flags, timeout);
break; break;
default: default:
rc = cs_ioctl_default(hpriv, chunks, num_chunks, &cs_seq, rc = cs_ioctl_default(hpriv, chunks, num_chunks, &cs_seq,
args->in.cs_flags); args->in.cs_flags, timeout);
break; break;
} }
......
...@@ -1245,6 +1245,7 @@ struct hl_userptr { ...@@ -1245,6 +1245,7 @@ struct hl_userptr {
* @sequence: the sequence number of this CS. * @sequence: the sequence number of this CS.
* @staged_sequence: the sequence of the staged submission this CS is part of, * @staged_sequence: the sequence of the staged submission this CS is part of,
* relevant only if staged_cs is set. * relevant only if staged_cs is set.
* @timeout_jiffies: cs timeout in jiffies.
* @type: CS_TYPE_*. * @type: CS_TYPE_*.
* @submitted: true if CS was submitted to H/W. * @submitted: true if CS was submitted to H/W.
* @completed: true if CS was completed by device. * @completed: true if CS was completed by device.
...@@ -1273,6 +1274,7 @@ struct hl_cs { ...@@ -1273,6 +1274,7 @@ struct hl_cs {
struct list_head debugfs_list; struct list_head debugfs_list;
u64 sequence; u64 sequence;
u64 staged_sequence; u64 staged_sequence;
u64 timeout_jiffies;
enum hl_cs_type type; enum hl_cs_type type;
u8 submitted; u8 submitted;
u8 completed; u8 completed;
......
...@@ -629,7 +629,7 @@ int hl_hw_queue_schedule_cs(struct hl_cs *cs) ...@@ -629,7 +629,7 @@ int hl_hw_queue_schedule_cs(struct hl_cs *cs)
if ((hdev->timeout_jiffies != MAX_SCHEDULE_TIMEOUT) && if ((hdev->timeout_jiffies != MAX_SCHEDULE_TIMEOUT) &&
first_entry && cs_needs_timeout(cs)) { first_entry && cs_needs_timeout(cs)) {
cs->tdr_active = true; cs->tdr_active = true;
schedule_delayed_work(&cs->work_tdr, hdev->timeout_jiffies); schedule_delayed_work(&cs->work_tdr, cs->timeout_jiffies);
} }
......
...@@ -630,6 +630,7 @@ struct hl_cs_chunk { ...@@ -630,6 +630,7 @@ struct hl_cs_chunk {
#define HL_CS_FLAGS_STAGED_SUBMISSION 0x40 #define HL_CS_FLAGS_STAGED_SUBMISSION 0x40
#define HL_CS_FLAGS_STAGED_SUBMISSION_FIRST 0x80 #define HL_CS_FLAGS_STAGED_SUBMISSION_FIRST 0x80
#define HL_CS_FLAGS_STAGED_SUBMISSION_LAST 0x100 #define HL_CS_FLAGS_STAGED_SUBMISSION_LAST 0x100
#define HL_CS_FLAGS_CUSTOM_TIMEOUT 0x200
#define HL_CS_STATUS_SUCCESS 0 #define HL_CS_STATUS_SUCCESS 0
...@@ -665,8 +666,18 @@ struct hl_cs_in { ...@@ -665,8 +666,18 @@ struct hl_cs_in {
*/ */
__u32 num_chunks_execute; __u32 num_chunks_execute;
/* Number of chunks in restore phase array - Currently not in use */ union {
__u32 num_chunks_store; /* Number of chunks in restore phase array -
* Currently not in use
*/
__u32 num_chunks_store;
/* timeout in seconds - valid only if HL_CS_FLAGS_CUSTOM_TIMEOUT
* is set. this parameter is ignored in case of future multiple
* users support.
*/
__u32 timeout;
};
/* HL_CS_FLAGS_* */ /* HL_CS_FLAGS_* */
__u32 cs_flags; __u32 cs_flags;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment