Proof with (try discriminate).
unfold divlu_mul_params; intros d m' p'.
destruct (find_div_mul_params Int64.wordsize
(Int64.modulus - Int64.modulus mod d - 1) d 64)
as [[p m] | ]...
generalize (p - 64); intro p1.
destruct (zlt 0 d)...
destruct (zle (two_p (64 + p1)) (m * d))...
destruct (zle (m * d) (two_p (64 + p1) + two_p p1))...
destruct (zle 0 m)...
destruct (zlt m Int64.modulus)...
destruct (zle 0 p1)...
destruct (zlt p1 64)...
intros EQ; inv EQ.
split. auto. split. auto. intros.
apply Zdiv_mul_pos; try omega. assumption.
Qed.
Remark int64_shr'_div_two_p:
forall x y, Int64.shr' x y = Int64.repr (Int64.signed x / two_p (Int.unsigned y)).

(* Specifications: *)
Lemma divls_mul_shift_gen:
forall x y m p,
divls_mul_params (Int64.signed y) = Some(p, m) ->
0 <= m < Int64.modulus /\ 0 <= p < 64 /\
Int64.divs x y = Int64.add (Int64.shr' (Int64.repr ((Int64.signed x * m) / Int64.modulus)) (Int.repr p))
(Int64.shru x (Int64.repr 63)).
Theorem divls_mul_shift_1:
forall x y m p,
divls_mul_params (Int64.signed y) = Some(p, m) ->
m < Int64.half_modulus ->
0 <= p < 64 /\
Int64.divs x y = Int64.add (Int64.shr' (Int64.mulhs x (Int64.repr m)) (Int.repr p))
(Int64.shru' x (Int.repr 63)).
Theorem divls_mul_shift_2:
forall x y m p,
divls_mul_params (Int64.signed y) = Some(p, m) ->
m >= Int64.half_modulus ->
0 <= p < 64 /\
Int64.divs x y = Int64.add (Int64.shr' (Int64.add (Int64.mulhs x (Int64.repr m)) x) (Int.repr p))
(Int64.shru' x (Int.repr 63)).