I think the following functions can be rewritten in plain AutoLisp by substituting dict* functions in place of ActiveX functions (though I haven't done that for you):
But wait, I don't know how to get the activedocument entity via plain AutoLisp.
Oh, I think you can...
(setq props (dictsearch (namedobjdict) "DwgProps"))
Hmm, it seems that DwgProps doesn't exist until a first entry is made, at least in 2002.
(defun @getdwgprops ( / Doc Dicts Props handle ent custom)
(vl-load-com)
(setq Doc (vla-get-activedocument (vlax-get-acad-object)))
(setq Dicts (vlax-get Doc 'Dictionaries))
(setq props (vla-item Dicts "DwgProps"))
(setq handle (vlax-get Props 'Handle))
(setq ent (entget (handent handle)))
(setq custom (vl-remove-if-not '(lambda (x)(<= 300 (car x) 309)) ent))
)
(defun @setdwgprop (ID Name Value / Doc Dicts Props handle e ent)
(and
(setq ok 1)
(or (vl-load-com) 1)
(setq ok 2)
(setq Doc (vla-get-activedocument (vlax-get-acad-object)))
(setq ok 3)
(setq Dicts (vlax-get Doc 'Dictionaries))
(setq ok 4)
(setq props (vla-item Dicts "DwgProps"))
(setq ok 5)
(setq handle (vlax-get Props 'Handle))
(setq ok 6)
(setq e (handent handle))
(setq ent (entget e))
(setq ok 7)
(or
(and (= (type ID) 'INT)(<= 300 ID 309))
(alert "ID must be an integer in the range from 300 to 309")
)
(setq ok 8)
(or (= (type Name) 'STR)
(alert "Name must be a string.")
)
(setq ok 9)
(or (= (type Value) 'STR)
(alert "Value must be a string.")
)
(setq ok 10)
(setq ent (subst (cons ID (strcat Name "=" Value))(assoc ID ent) ent))
(entmod ent)
(setq ok 11)
(entupd e)
(setq ok 12)
)
ent
)
Note that the ok statements were just my way of finding where I had blundered. You can eliminate them without any adverse effects.