1
0
mirror of https://github.com/postgres/postgres.git synced 2025-05-28 05:21:27 +03:00

Last-minute updates for release notes.

Security: CVE-2017-7546, CVE-2017-7547, CVE-2017-7548
This commit is contained in:
Tom Lane 2017-08-07 11:46:20 -04:00
parent 5e8e009146
commit d64440f5fb
2 changed files with 256 additions and 142 deletions

View File

@ -29,7 +29,12 @@
</para>
<para>
However, if you are upgrading from a version earlier than 9.2.20,
However, if you use foreign data servers that make use of user
passwords for authentication, see the first changelog entry below.
</para>
<para>
Also, if you are upgrading from a version earlier than 9.2.20,
see <xref linkend="release-9-2-20">.
</para>
@ -40,6 +45,126 @@
<itemizedlist>
<listitem>
<para>
Further restrict visibility
of <structname>pg_user_mappings</>.<structfield>umoptions</>, to
protect passwords stored as user mapping options
(Noah Misch)
</para>
<para>
The fix for CVE-2017-7486 was incorrect: it allowed a user
to see the options in her own user mapping, even if she did not
have <literal>USAGE</> permission on the associated foreign server.
Such options might include a password that had been provided by the
server owner rather than the user herself.
Since <structname>information_schema.user_mapping_options</> does not
show the options in such cases, <structname>pg_user_mappings</>
should not either.
(CVE-2017-7547)
</para>
<para>
By itself, this patch will only fix the behavior in newly initdb'd
databases. If you wish to apply this change in an existing database,
you will need to do the following:
</para>
<procedure>
<step>
<para>
Restart the postmaster after adding <literal>allow_system_table_mods
= true</> to <filename>postgresql.conf</>. (In versions
supporting <command>ALTER SYSTEM</>, you can use that to make the
configuration change, but you'll still need a restart.)
</para>
</step>
<step>
<para>
In <emphasis>each</> database of the cluster,
run the following commands as superuser:
<programlisting>
SET search_path = pg_catalog;
CREATE OR REPLACE VIEW pg_user_mappings AS
SELECT
U.oid AS umid,
S.oid AS srvid,
S.srvname AS srvname,
U.umuser AS umuser,
CASE WHEN U.umuser = 0 THEN
'public'
ELSE
A.rolname
END AS usename,
CASE WHEN (U.umuser &lt;&gt; 0 AND A.rolname = current_user
AND (pg_has_role(S.srvowner, 'USAGE')
OR has_server_privilege(S.oid, 'USAGE')))
OR (U.umuser = 0 AND pg_has_role(S.srvowner, 'USAGE'))
OR (SELECT rolsuper FROM pg_authid WHERE rolname = current_user)
THEN U.umoptions
ELSE NULL END AS umoptions
FROM pg_user_mapping U
LEFT JOIN pg_authid A ON (A.oid = U.umuser) JOIN
pg_foreign_server S ON (U.umserver = S.oid);
</programlisting>
</para>
</step>
<step>
<para>
Do not forget to include the <literal>template0</>
and <literal>template1</> databases, or the vulnerability will still
exist in databases you create later. To fix <literal>template0</>,
you'll need to temporarily make it accept connections.
In <productname>PostgreSQL</> 9.5 and later, you can use
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS true;
</programlisting>
and then after fixing <literal>template0</>, undo that with
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS false;
</programlisting>
In prior versions, instead use
<programlisting>
UPDATE pg_database SET datallowconn = true WHERE datname = 'template0';
UPDATE pg_database SET datallowconn = false WHERE datname = 'template0';
</programlisting>
</para>
</step>
<step>
<para>
Finally, remove the <literal>allow_system_table_mods</> configuration
setting, and again restart the postmaster.
</para>
</step>
</procedure>
</listitem>
<listitem>
<para>
Disallow empty passwords in all password-based authentication methods
(Heikki Linnakangas)
</para>
<para>
<application>libpq</> ignores empty password specifications, and does
not transmit them to the server. So, if a user's password has been
set to the empty string, it's impossible to log in with that password
via <application>psql</> or other <application>libpq</>-based
clients. An administrator might therefore believe that setting the
password to empty is equivalent to disabling password login.
However, with a modified or non-<application>libpq</>-based client,
logging in could be possible, depending on which authentication
method is configured. In particular the most common
method, <literal>md5</>, accepted empty passwords.
Change the server to reject empty passwords in all cases.
(CVE-2017-7546)
</para>
</listitem>
<listitem>
<para>
On Windows, retry process creation if we fail to reserve the address
@ -410,77 +535,9 @@
<para>
By itself, this patch will only fix the behavior in newly initdb'd
databases. If you wish to apply this change in an existing database,
you will need to do the following:
follow the corrected procedure shown in the changelog entry for
CVE-2017-7547, in <xref linkend="release-9-2-22">.
</para>
<procedure>
<step>
<para>
Restart the postmaster after adding <literal>allow_system_table_mods
= true</> to <filename>postgresql.conf</>. (In versions
supporting <command>ALTER SYSTEM</>, you can use that to make the
configuration change, but you'll still need a restart.)
</para>
</step>
<step>
<para>
In <emphasis>each</> database of the cluster,
run the following commands as superuser:
<programlisting>
SET search_path = pg_catalog;
CREATE OR REPLACE VIEW pg_user_mappings AS
SELECT
U.oid AS umid,
S.oid AS srvid,
S.srvname AS srvname,
U.umuser AS umuser,
CASE WHEN U.umuser = 0 THEN
'public'
ELSE
A.rolname
END AS usename,
CASE WHEN (U.umuser &lt;&gt; 0 AND A.rolname = current_user)
OR (U.umuser = 0 AND pg_has_role(S.srvowner, 'USAGE'))
OR (SELECT rolsuper FROM pg_authid WHERE rolname = current_user)
THEN U.umoptions
ELSE NULL END AS umoptions
FROM pg_user_mapping U
LEFT JOIN pg_authid A ON (A.oid = U.umuser) JOIN
pg_foreign_server S ON (U.umserver = S.oid);
</programlisting>
</para>
</step>
<step>
<para>
Do not forget to include the <literal>template0</>
and <literal>template1</> databases, or the vulnerability will still
exist in databases you create later. To fix <literal>template0</>,
you'll need to temporarily make it accept connections.
In <productname>PostgreSQL</> 9.5 and later, you can use
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS true;
</programlisting>
and then after fixing <literal>template0</>, undo that with
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS false;
</programlisting>
In prior versions, instead use
<programlisting>
UPDATE pg_database SET datallowconn = true WHERE datname = 'template0';
UPDATE pg_database SET datallowconn = false WHERE datname = 'template0';
</programlisting>
</para>
</step>
<step>
<para>
Finally, remove the <literal>allow_system_table_mods</> configuration
setting, and again restart the postmaster.
</para>
</step>
</procedure>
</listitem>
<listitem>

View File

@ -23,7 +23,12 @@
</para>
<para>
However, if you are upgrading from a version earlier than 9.3.16,
However, if you use foreign data servers that make use of user
passwords for authentication, see the first changelog entry below.
</para>
<para>
Also, if you are upgrading from a version earlier than 9.3.16,
see <xref linkend="release-9-3-16">.
</para>
@ -34,6 +39,126 @@
<itemizedlist>
<listitem>
<para>
Further restrict visibility
of <structname>pg_user_mappings</>.<structfield>umoptions</>, to
protect passwords stored as user mapping options
(Noah Misch)
</para>
<para>
The fix for CVE-2017-7486 was incorrect: it allowed a user
to see the options in her own user mapping, even if she did not
have <literal>USAGE</> permission on the associated foreign server.
Such options might include a password that had been provided by the
server owner rather than the user herself.
Since <structname>information_schema.user_mapping_options</> does not
show the options in such cases, <structname>pg_user_mappings</>
should not either.
(CVE-2017-7547)
</para>
<para>
By itself, this patch will only fix the behavior in newly initdb'd
databases. If you wish to apply this change in an existing database,
you will need to do the following:
</para>
<procedure>
<step>
<para>
Restart the postmaster after adding <literal>allow_system_table_mods
= true</> to <filename>postgresql.conf</>. (In versions
supporting <command>ALTER SYSTEM</>, you can use that to make the
configuration change, but you'll still need a restart.)
</para>
</step>
<step>
<para>
In <emphasis>each</> database of the cluster,
run the following commands as superuser:
<programlisting>
SET search_path = pg_catalog;
CREATE OR REPLACE VIEW pg_user_mappings AS
SELECT
U.oid AS umid,
S.oid AS srvid,
S.srvname AS srvname,
U.umuser AS umuser,
CASE WHEN U.umuser = 0 THEN
'public'
ELSE
A.rolname
END AS usename,
CASE WHEN (U.umuser &lt;&gt; 0 AND A.rolname = current_user
AND (pg_has_role(S.srvowner, 'USAGE')
OR has_server_privilege(S.oid, 'USAGE')))
OR (U.umuser = 0 AND pg_has_role(S.srvowner, 'USAGE'))
OR (SELECT rolsuper FROM pg_authid WHERE rolname = current_user)
THEN U.umoptions
ELSE NULL END AS umoptions
FROM pg_user_mapping U
LEFT JOIN pg_authid A ON (A.oid = U.umuser) JOIN
pg_foreign_server S ON (U.umserver = S.oid);
</programlisting>
</para>
</step>
<step>
<para>
Do not forget to include the <literal>template0</>
and <literal>template1</> databases, or the vulnerability will still
exist in databases you create later. To fix <literal>template0</>,
you'll need to temporarily make it accept connections.
In <productname>PostgreSQL</> 9.5 and later, you can use
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS true;
</programlisting>
and then after fixing <literal>template0</>, undo that with
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS false;
</programlisting>
In prior versions, instead use
<programlisting>
UPDATE pg_database SET datallowconn = true WHERE datname = 'template0';
UPDATE pg_database SET datallowconn = false WHERE datname = 'template0';
</programlisting>
</para>
</step>
<step>
<para>
Finally, remove the <literal>allow_system_table_mods</> configuration
setting, and again restart the postmaster.
</para>
</step>
</procedure>
</listitem>
<listitem>
<para>
Disallow empty passwords in all password-based authentication methods
(Heikki Linnakangas)
</para>
<para>
<application>libpq</> ignores empty password specifications, and does
not transmit them to the server. So, if a user's password has been
set to the empty string, it's impossible to log in with that password
via <application>psql</> or other <application>libpq</>-based
clients. An administrator might therefore believe that setting the
password to empty is equivalent to disabling password login.
However, with a modified or non-<application>libpq</>-based client,
logging in could be possible, depending on which authentication
method is configured. In particular the most common
method, <literal>md5</>, accepted empty passwords.
Change the server to reject empty passwords in all cases.
(CVE-2017-7546)
</para>
</listitem>
<listitem>
<para>
Fix concurrent locking of tuple update chains (&Aacute;lvaro Herrera)
@ -497,77 +622,9 @@
<para>
By itself, this patch will only fix the behavior in newly initdb'd
databases. If you wish to apply this change in an existing database,
you will need to do the following:
follow the corrected procedure shown in the changelog entry for
CVE-2017-7547, in <xref linkend="release-9-3-18">.
</para>
<procedure>
<step>
<para>
Restart the postmaster after adding <literal>allow_system_table_mods
= true</> to <filename>postgresql.conf</>. (In versions
supporting <command>ALTER SYSTEM</>, you can use that to make the
configuration change, but you'll still need a restart.)
</para>
</step>
<step>
<para>
In <emphasis>each</> database of the cluster,
run the following commands as superuser:
<programlisting>
SET search_path = pg_catalog;
CREATE OR REPLACE VIEW pg_user_mappings AS
SELECT
U.oid AS umid,
S.oid AS srvid,
S.srvname AS srvname,
U.umuser AS umuser,
CASE WHEN U.umuser = 0 THEN
'public'
ELSE
A.rolname
END AS usename,
CASE WHEN (U.umuser &lt;&gt; 0 AND A.rolname = current_user)
OR (U.umuser = 0 AND pg_has_role(S.srvowner, 'USAGE'))
OR (SELECT rolsuper FROM pg_authid WHERE rolname = current_user)
THEN U.umoptions
ELSE NULL END AS umoptions
FROM pg_user_mapping U
LEFT JOIN pg_authid A ON (A.oid = U.umuser) JOIN
pg_foreign_server S ON (U.umserver = S.oid);
</programlisting>
</para>
</step>
<step>
<para>
Do not forget to include the <literal>template0</>
and <literal>template1</> databases, or the vulnerability will still
exist in databases you create later. To fix <literal>template0</>,
you'll need to temporarily make it accept connections.
In <productname>PostgreSQL</> 9.5 and later, you can use
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS true;
</programlisting>
and then after fixing <literal>template0</>, undo that with
<programlisting>
ALTER DATABASE template0 WITH ALLOW_CONNECTIONS false;
</programlisting>
In prior versions, instead use
<programlisting>
UPDATE pg_database SET datallowconn = true WHERE datname = 'template0';
UPDATE pg_database SET datallowconn = false WHERE datname = 'template0';
</programlisting>
</para>
</step>
<step>
<para>
Finally, remove the <literal>allow_system_table_mods</> configuration
setting, and again restart the postmaster.
</para>
</step>
</procedure>
</listitem>
<listitem>